1.修复有地形情况下,绘制多边形边缘线无法贴地的情况;2.修改水源地(面)显示水面动态纹理;

This commit is contained in:
zhangquan 2025-07-14 17:46:09 +08:00
parent ec4ca333b2
commit 8e6a168c37
10 changed files with 129 additions and 68 deletions

View File

@ -0,0 +1,16 @@
import * as Cesium from "cesium";
export default class FeatureGroundPrimitive extends Cesium.GroundPrimitive {
properties = new Cesium.PropertyBag()
constructor(options, properties) {
super(options);
if(properties && properties instanceof Object) {
for (const key in properties) {
if (Object.prototype.hasOwnProperty.call(properties, key)) {
this.properties.addProperty(key, properties[key]);
}
}
}
}
}

View File

@ -67,7 +67,7 @@ export const drawAttackArrow = (deps) => {
const pts = createAttackArrowPositions(positions) const pts = createAttackArrowPositions(positions)
return [...pts, pts[0]] return [...pts, pts[0]]
}, false), }, false),
// clampToGround: true, // 多边形边界线通常不需要 clampToGround因为多边形本身已经处理了高度 clampToGround: true,
width: 2, width: 2,
material: CesiumColor.fromCssColorString('#ff0000'), material: CesiumColor.fromCssColorString('#ff0000'),
}, },

View File

@ -62,7 +62,7 @@ export const drawCurvePolygon = (deps) => {
} }
return createCurvePolygonPositions(positions) return createCurvePolygonPositions(positions)
}, false), }, false),
// clampToGround: true, // 多边形边界线通常不需要 clampToGround因为多边形本身已经处理了高度 clampToGround: true,
width: 2, width: 2,
material: CesiumColor.fromCssColorString('#ff0000'), material: CesiumColor.fromCssColorString('#ff0000'),
}, },

View File

@ -67,7 +67,7 @@ export const drawDoubleArrow = (deps) => {
const pts = createDoubleArrowPositions(positions) const pts = createDoubleArrowPositions(positions)
return [...pts, pts[0]] return [...pts, pts[0]]
}, false), }, false),
// clampToGround: true, // 多边形边界线通常不需要 clampToGround因为多边形本身已经处理了高度 clampToGround: true,
width: 2, width: 2,
material: CesiumColor.fromCssColorString('#ff0000'), material: CesiumColor.fromCssColorString('#ff0000'),
}, },

View File

@ -64,6 +64,7 @@ export const drawPolygon = (deps) => {
// clampToGround: true, // 多边形边界线通常不需要 clampToGround因为多边形本身已经处理了高度 // clampToGround: true, // 多边形边界线通常不需要 clampToGround因为多边形本身已经处理了高度
width: 2, width: 2,
material: CesiumColor.fromCssColorString('#ff0000'), material: CesiumColor.fromCssColorString('#ff0000'),
clampToGround: true,
}, },
}) })

View File

@ -63,7 +63,7 @@ export const drawStraightArrow = (deps) => {
const pts = createStraightArrowPositions(positions) const pts = createStraightArrowPositions(positions)
return [...pts, pts[0]] return [...pts, pts[0]]
}, false), }, false),
// clampToGround: true, // 多边形边界线通常不需要 clampToGround因为多边形本身已经处理了高度 clampToGround: true,
width: 2, width: 2,
material: CesiumColor.fromCssColorString('#ff0000'), material: CesiumColor.fromCssColorString('#ff0000'),
}, },

View File

@ -64,7 +64,7 @@ export const drawWideArrow = (deps) => {
return [...pts, pts[0]] return [...pts, pts[0]]
// return [...pts] // return [...pts]
}, false), }, false),
// clampToGround: true, // 多边形边界线通常不需要 clampToGround因为多边形本身已经处理了高度 clampToGround: true,
width: 2, width: 2,
material: CesiumColor.fromCssColorString('#ff0000'), material: CesiumColor.fromCssColorString('#ff0000'),
}, },

View File

@ -6,6 +6,7 @@ import {
Entity, Entity,
CallbackPositionProperty, CallbackPositionProperty,
Color as CesiumColor, Color as CesiumColor,
HeightReference,
} from 'cesium' } from 'cesium'
import { useEventBus } from '../useEventBus' import { useEventBus } from '../useEventBus'
import { useHoverPosition } from '../useHoverPosition' import { useHoverPosition } from '../useHoverPosition'
@ -69,9 +70,8 @@ export const useDrawTool = (viewer) => {
color: CesiumColor.BLUE, color: CesiumColor.BLUE,
outlineColor: CesiumColor.WHITE, outlineColor: CesiumColor.WHITE,
outlineWidth: 1, outlineWidth: 1,
heightReference: HeightReference.CLAMP_TO_GROUND,
}, },
// 可以考虑是否需要 HeightReference.CLAMP_TO_GROUND
// heightReference: HeightReference.CLAMP_TO_GROUND,
}) })
viewer.entities.add(assistPoint) viewer.entities.add(assistPoint)

View File

@ -29,6 +29,7 @@ import {
import { useEventBus } from '@/components/CesiumMap/mixins/useEventBus'; import { useEventBus } from '@/components/CesiumMap/mixins/useEventBus';
import { useMeasureTool, getArea, getBoundingCenterCoordinate } from '@/components/CesiumMap/mixins/useMeasureTool'; import { useMeasureTool, getArea, getBoundingCenterCoordinate } from '@/components/CesiumMap/mixins/useMeasureTool';
import { setPropertyData } from './DialogPropertyGrid/property'; import { setPropertyData } from './DialogPropertyGrid/property';
import FeatureGroundPrimitive from '@/components/CesiumMap/FeatureGroundPrimitive';
import toolbarLocationIcon from '@/assets/icons/toolbar_location.png'; import toolbarLocationIcon from '@/assets/icons/toolbar_location.png';
import toolbarPolylineIcon from '@/assets/icons/toolbar_polyline.png'; import toolbarPolylineIcon from '@/assets/icons/toolbar_polyline.png';
@ -59,6 +60,7 @@ let drawTool = null
let measureTool = null let measureTool = null
let bus = null let bus = null
let toolbarLayer = null let toolbarLayer = null
let primitiveList = []
const isOpen = ref(false) const isOpen = ref(false)
const options = ref([{ const options = ref([{
name: 'location', name: 'location',
@ -128,7 +130,8 @@ const drawLocation = (params) => {
position, position,
billboard: { billboard: {
image: params?.icon || drawLocationIcon, image: params?.icon || drawLocationIcon,
verticalOrigin: Cesium.VerticalOrigin.BOTTOM verticalOrigin: Cesium.VerticalOrigin.BOTTOM,
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
} }
}); });
}); });
@ -148,6 +151,7 @@ const drawPolyline = () => {
positions, positions,
width: 2, width: 2,
material: Cesium.Color.YELLOW, material: Cesium.Color.YELLOW,
clampToGround: true,
}, },
}) })
}); });
@ -167,10 +171,12 @@ const drawPolygon = () => {
positions:[...positions, positions[0]], // positions:[...positions, positions[0]], //
width: 2, width: 2,
material: Cesium.Color.YELLOW, material: Cesium.Color.YELLOW,
clampToGround: true,
}, },
polygon: { polygon: {
hierarchy: positions, hierarchy: positions,
material: Cesium.Color.YELLOW.withAlpha(0.5), material: Cesium.Color.YELLOW.withAlpha(0.5),
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
}, },
}); });
}); });
@ -193,10 +199,12 @@ const drawCurvePolygon = () => {
positions: fullPositions, positions: fullPositions,
width: 2, width: 2,
material: Cesium.Color.YELLOW, material: Cesium.Color.YELLOW,
clampToGround: true,
}, },
polygon: { polygon: {
hierarchy: fullPositions, hierarchy: fullPositions,
material: Cesium.Color.YELLOW.withAlpha(0.5), material: Cesium.Color.YELLOW.withAlpha(0.5),
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
}, },
}); });
}); });
@ -219,10 +227,12 @@ const drawStraightArrow = () => {
positions: [...fullPositions, fullPositions[0]], positions: [...fullPositions, fullPositions[0]],
width: 2, width: 2,
material: Cesium.Color.YELLOW, material: Cesium.Color.YELLOW,
clampToGround: true,
}, },
polygon: { polygon: {
hierarchy: fullPositions, hierarchy: fullPositions,
material: Cesium.Color.YELLOW.withAlpha(0.5), material: Cesium.Color.YELLOW.withAlpha(0.5),
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
}, },
}) })
}); });
@ -245,10 +255,12 @@ const drawWideArrow = () => {
positions: [...fullPositions, fullPositions[0]], positions: [...fullPositions, fullPositions[0]],
width: 2, width: 2,
material: Cesium.Color.YELLOW, material: Cesium.Color.YELLOW,
clampToGround: true,
}, },
polygon: { polygon: {
hierarchy: fullPositions, hierarchy: fullPositions,
material: Cesium.Color.YELLOW.withAlpha(0.5), material: Cesium.Color.YELLOW.withAlpha(0.5),
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
}, },
}) })
}); });
@ -271,10 +283,12 @@ const drawAttackArrow = () => {
positions: [...fullPositions, fullPositions[0]], positions: [...fullPositions, fullPositions[0]],
width: 2, width: 2,
material: Cesium.Color.YELLOW, material: Cesium.Color.YELLOW,
clampToGround: true,
}, },
polygon: { polygon: {
hierarchy: fullPositions, hierarchy: fullPositions,
material: Cesium.Color.YELLOW.withAlpha(0.5), material: Cesium.Color.YELLOW.withAlpha(0.5),
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
}, },
}) })
}); });
@ -297,10 +311,12 @@ const drawDoubleArrow = () => {
positions: [...fullPositions, fullPositions[0]], positions: [...fullPositions, fullPositions[0]],
width: 2, width: 2,
material: Cesium.Color.YELLOW, material: Cesium.Color.YELLOW,
clampToGround: true,
}, },
polygon: { polygon: {
hierarchy: fullPositions, hierarchy: fullPositions,
material: Cesium.Color.YELLOW.withAlpha(0.5), material: Cesium.Color.YELLOW.withAlpha(0.5),
heightReference: Cesium.HeightReference.CLAMP_TO_GROUND,
}, },
}) })
}); });
@ -342,31 +358,82 @@ const drawWatersource = () => {
drawTool.drawPolygon().then((positions) => { drawTool.drawPolygon().then((positions) => {
// //
const center = getBoundingCenterCoordinate(positions); const center = getBoundingCenterCoordinate(positions);
//
const entity = toolbarLayer?.entities.add({ // //
polyline: { // const entity = toolbarLayer?.entities.add({
positions:[...positions, positions[0]], // // // polyline: {
width: 2, // // positions:[...positions, positions[0]], //
material: Cesium.Color.BLUE, // // width: 2,
}, // // material: Cesium.Color.BLUE,
polygon: { // // },
hierarchy: positions, // polygon: {
material: Cesium.Color.BLUE.withAlpha(0.5), // hierarchy: positions,
}, // material: riverMaterial,
properties: { // // material: Cesium.Color.BLUE.withAlpha(0.5),
__type: 'watersource', // },
name: '', // properties: {
area: getArea(positions).toFixed(2), // // __type: 'watersource',
longitude: center[0].toFixed(6), // name: '',
latitude: center[1].toFixed(6), // area: getArea(positions).toFixed(2), //
volume: 0 // 0 // longitude: center[0].toFixed(6),
// latitude: center[1].toFixed(6),
// volume: 0 // 0
// }
// });
const waterMaterial = new Cesium.Material({
fabric: {
type: 'Water',
uniforms: {
normalMap: Cesium.buildModuleUrl('Assets/Textures/waterNormals.jpg'),
baseWaterColor: new Cesium.Color(
64 / 255.0,
157 / 255.0,
253 / 255.0,
0.6
),
// blendColor: new Cesium.Color(0.0, 0.5, 1.0, 1.0),
// frequency: 10.0,
// animationSpeed: 0.05,
// amplitude: 10,
// specularIntensity: 0.5,
// alpha: 0.1
frequency: 1000.0,
animationSpeed: 0.1,
amplitude: 10,
specularIntensity: 1.5,
}
} }
}); });
const waterPrimitive = new FeatureGroundPrimitive({
geometryInstances: new Cesium.GeometryInstance({
geometry: new Cesium.PolygonGeometry({
polygonHierarchy: new Cesium.PolygonHierarchy(positions),
vertexFormat: Cesium.EllipsoidSurfaceAppearance.VERTEX_FORMAT,
})
}),
appearance: new Cesium.EllipsoidSurfaceAppearance({
material: waterMaterial,
})
}, {
__type: 'watersource',
name: '',
area: getArea(positions).toFixed(2), //
longitude: center[0].toFixed(6),
latitude: center[1].toFixed(6),
volume: 0 // 0
});
// Primitive
viewer.scene.primitives.add(waterPrimitive);
primitiveList.push(waterPrimitive);
// //
DialogPropertyGrid.show(entity, (data) => { DialogPropertyGrid.show(waterPrimitive, (data) => {
// console.log(':', formData); // console.log(':', formData);
// //
setPropertyData(data, entity); setPropertyData(data, waterPrimitive);
// //
}); });
}); });
@ -414,6 +481,14 @@ const toolbarClear = () => {
// //
toolbarLayer.entities.removeAll(); toolbarLayer.entities.removeAll();
//
for (let index = primitiveList.length - 1; index >= 0; index--) {
const p = primitiveList[index];
if(viewer.scene.primitives.contains(p)) {
viewer.scene.primitives.remove(p);
primitiveList.splice(index, 1);
}
}
measureTool?.clear(); measureTool?.clear();
// //

View File

@ -14,6 +14,7 @@ import { useEventBus } from '@/components/CesiumMap/mixins/useEventBus';
import Toolbar from './Toolbar.vue'; import Toolbar from './Toolbar.vue';
import DialogPropertyGrid from './DialogPropertyGrid'; import DialogPropertyGrid from './DialogPropertyGrid';
import { setPropertyData } from './DialogPropertyGrid/property'; import { setPropertyData } from './DialogPropertyGrid/property';
import FeatureGroundPrimitive from '@/components/CesiumMap/FeatureGroundPrimitive';
const viewerRef = shallowRef(null) const viewerRef = shallowRef(null)
const options = ref({ const options = ref({
@ -27,6 +28,7 @@ const options = ref({
roll: 0 // roll: 0 //
}, },
ditu: 'tianditu', // ditu: 'tianditu', //
isTerrainProvider: true, //
}) })
const showProperty = ref(false); // const showProperty = ref(false); //
const propertyData = ref([]) const propertyData = ref([])
@ -48,7 +50,7 @@ const initMap = (v) => {
// //
for (let index = 0; index < pickedObjectList.length; index++) { for (let index = 0; index < pickedObjectList.length; index++) {
const obj = pickedObjectList[index]; const obj = pickedObjectList[index];
if (Cesium.defined(obj) && obj.id && obj.id instanceof Cesium.Entity) { if (obj && obj.id && obj.id instanceof Cesium.Entity) {
// name'__' // name'__'
if(obj.id.name?.indexOf('__') === 0) { if(obj.id.name?.indexOf('__') === 0) {
continue continue
@ -60,51 +62,18 @@ const initMap = (v) => {
// //
}) })
return return
} else if(obj.primitive && obj.primitive instanceof FeatureGroundPrimitive) {
DialogPropertyGrid.show(obj.primitive, (data) => {
//
setPropertyData(data, obj.primitive);
//
})
} }
} }
} }
}) })
}; };
//
// propertyData.value = [
// { key: 'id', name: 'ID', value: '12345', type: 'text', disabled: true },
// { key: 'title', name: '', value: '', type: 'text', checkMethod: (val) => val.length > 0 || (ElMessage.error(''), false) },
// { key: 'fontSize', name: '', value: 16, type: 'number', checkMethod: (val) => val >= 12 && val <= 72 || (ElMessage.error('12-72'), false) },
// {
// key: 'align',
// name: '',
// value: 'left',
// type: 'select',
// options: [
// { label: '', value: 'left' },
// { label: '', value: 'center' },
// { label: '', value: 'right' },
// ],
// checkMethod: (val) => ['left', 'center', 'right'].includes(val) || (ElMessage.error(''), false)
// },
// { key: 'color', name: '', value: '#409EFF', type: 'color' },
// { key: 'visible', name: '', value: true, type: 'select', options: [{ label: '', value: true }, { label: '', value: false }] },
// { key: 'description', name: '', value: '', type: 'text' },
// { key: 'padding', name: '', value: 10, type: 'number', checkMethod: (val) => val >= 0 || (ElMessage.error(''), false) },
// ];
//
const handlePropertyChange = (key, newValue, property) => {
console.log(`属性 "${property.name}" (key: ${key}) 的值变更为:`, newValue);
//
// internalData使
// properties key
//
// const index = properties.value.findIndex(item => item.key === key);
// if (index !== -1) {
// properties.value[index].value = newValue;
// }
// properties.value[index].value properties ref
// properties props
// properties ref
};
</script> </script>
<style lang="scss" scoped> <style lang="scss" scoped>