There is a Cartesian3 {x: -1270054.670468495, y: 5643182.82695817, z: 2678382.5261573032}
It has no height. How to turn it into a high Cartesian3,It is similar to heightReference: HeightReference.RELATIVE_TO_GROUND set by entity?
Or entity is set to heightReference: HeightReference.RELATIVE_TO_GROUND, how to get the actual cartesian3?
Hi @mcck! It was my understanding that the third coordinate in Cartesian3 represented elevation. Can you please share some more details on your high-level goals here?
Yes, it can be calculated from your Cartesian, but the one you provided in the first post has actually a height of 4.656612873077393e-10 so its ~0.
Anyways, here is a Sandcastle link with height-calculation: link
If you need heigth, either you need some source of height-information or set it to a random height.
Maybe I can’t describe it clearly, but I may have found a way
let cartographic = Cesium.Cartographic.fromCartesian(cartesian3);
let longitude = Cesium.Math.toDegrees(cartographic.longitude);
let latitude = Cesium.Math.toDegrees(cartographic.latitude);
let height = viewer.scene.globe.getHeight(cartographic);
let cartesian3Height = Cesium.Cartesian3.fromDegrees(longitude, latitude, height);
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<!-- Include the CesiumJS JavaScript and CSS files -->
<script src="https://cesium.com/downloads/cesiumjs/releases/1.89/Build/Cesium/Cesium.js"></script>
<link href="https://cesium.com/downloads/cesiumjs/releases/1.89/Build/Cesium/Widgets/widgets.css" rel="stylesheet">
<style>
html,body,#cesiumContainer{
height: 100%;
width: 100%;
padding: 0;
margin: 0;
}
#tips{
position: fixed;
width: 100px;
height: 100px;
line-height: 100px;
background-color: #FFF;
text-align: center;
}
</style>
</head>
<body>
<div id="cesiumContainer"></div>
<div id="tips">hello</div>
<script>
Cesium.Ion.defaultAccessToken = 'eyJhbGciOiJIUzI1NiIsInR5cCI6IkpXVCJ9.eyJqdGkiOiI2NDE1MWIyMC02N2VmLTQwMzktOGQyNS0wMGY0MGVhOGQ5MDciLCJpZCI6NzUzNDMsImlhdCI6MTYzODUxNjc2MH0.NZMzdh31fcCJoL8tmcd46XdxTqiV_WoL4C9B3R5N-kM';
const viewer = new Cesium.Viewer('cesiumContainer', {
terrainProvider: Cesium.createWorldTerrain()
});
viewer.camera.setView({
destination : Cesium.Cartesian3.fromDegrees(100.23040561319219, 25.623343397054466, 4000),
orientation : {
heading : Cesium.Math.toRadians(-100),
pitch : Cesium.Math.toRadians(-15.0),
}
});
// Add a point
let cartesian3 = Cesium.Cartesian3.fromDegrees(100.1751884398384, 25.617734639164404); // Only longitude and latitude,No elevation
let point = viewer.entities.add({
position: cartesian3,
point: {
color: Cesium.Color.WHITE,
pixelSize: 10,
heightReference: Cesium.HeightReference.RELATIVE_TO_GROUND,
outlineColor: Cesium.Color.BLACK,
outlineWidth: 1
}
});
let tipDom = document.getElementById('tips');
let eventHandler = new Cesium.ScreenSpaceEventHandler(viewer.canvas);
eventHandler.setInputAction(() => {
let cartographic = Cesium.Cartographic.fromCartesian(cartesian3);
let longitude = Cesium.Math.toDegrees(cartographic.longitude);
let latitude = Cesium.Math.toDegrees(cartographic.latitude);
let height = viewer.scene.globe.getHeight(cartographic);
let cartesian3Height = Cesium.Cartesian3.fromDegrees(longitude, latitude, height);
let pos = Cesium.SceneTransforms.wgs84ToWindowCoordinates(viewer.scene, cartesian3Height); // No elevation, tipdom positioning error
if (pos) {
tipDom.style.top = pos.y + 'px';
tipDom.style.left = pos.x + 'px';
}
}, Cesium.ScreenSpaceEventType.MOUSE_MOVE);
</script>
<script>
new Cesium.ScreenSpaceEventHandler(viewer.canvas).setInputAction((action) => {
console.log("屏幕:", action.position);
let cartesian3 = viewer.scene.globe.pick(viewer.camera.getPickRay(action.position), viewer.scene);
console.log("Cartesian3:", cartesian3);
let cartographic = Cesium.Cartographic.fromCartesian(cartesian3);
console.log("经纬度:", {
latitude: Cesium.Math.toDegrees(cartographic.latitude),
longitude: Cesium.Math.toDegrees(cartographic.longitude),
height: cartographic.height
});
}, Cesium.ScreenSpaceEventType.LEFT_CLICK);
</script>
</div>
</body>
</html>
Thats indeed a viable solution!
Be aware that terrain needs some time to load, so until it is loaded you will get height = undefined with this method. But as you put it in a EventHandler it should not be a problem in this case.
It sounds like you sorted this out but nobody explained the fundamental nature of the problem.
Cartesian3 is for representing x/y/z coordinates in 3D space relative to the center of the earth. What you’re actually talking about is GPS coordinates on the surface of the earth. Cesium represents this concept with Cartographic. Latitude and longitude are natively stored in radians (angle across the ellipsoid’s surface), but the structure is commonly constructed using Cartographic.fromDegrees. If you model your position using Cartographic, you can easily modify the altitude (above ellipsoid surface) by changing its height property. Cartographics can be converted to Cartesian3 using the static Cartograhic.toCartesian function.