已知世界坐标系中的两个点p1、p2,求p1和p2的角度。原理是以p1为原点,建立一个enu坐标系,求出在这个相对坐标系中p1到p2的向量,归一化得到单位向量localVector,再通过Math.atan2计算出这个localVector和x轴的夹角,即是p1到p2的夹角。
方法一:先求出p1、p2在相对坐标系中的坐标local1、local2,相减得到向量localVector,归一化得到单位向量。
let localToWorldMatrix = Cesium.Transforms.eastNorthUpToFixedFrame(p1);
let worldToLocalMatrix = Cesium.Matrix4.inverse(localToWorldMatrix, new Cesium.Matrix4());
// 计算 localVector
let local1 = Cesium.Matrix4.multiplyByPoint(
worldToLocalMatrix,
p1,
new Cesium.Cartesian3()
);
let local2 = Cesium.Matrix4.multiplyByPoint(
worldToLocalMatrix,
p2,
new Cesium.Cartesian3()
);
let localVector = Cesium.Cartesian3.subtract(local2, local1, new Cesium.Cartesian3());
// localVector 向量归一化
let direction = Cesium.Cartesian3.normalize(localVector, new Cesium.Cartesian3());
let angleToX = Math.atan2(direction.y, direction.x);
let heading = Cesium.Math.toDegrees(angleToX);
方法二:先用p1、p2在世界坐标系中相减得到世界坐标下的向量worldVector,再用以p1为原点得到的矩阵的逆矩阵,计算出worldVector在相对坐标系下的向量值,归一化得到单位向量。
let localToWorldMatrix = Cesium.Transforms.eastNorthUpToFixedFrame(p1);
let worldToLocalMatrix = Cesium.Matrix4.inverse(localToWorldMatrix, new Cesium.Matrix4());
// 计算 localVector
let worldVector = Cesium.Cartesian3.subtract(p2, p1, new Cesium.Cartesian3());
let localVector = Cesium.Matrix4.multiplyByPointAsVector(worldToLocalMatrix, worldVector, new Cesium.Cartesian3());
// localVector 向量归一化
let direction = Cesium.Cartesian3.normalize(localVector, new Cesium.Cartesian3());
let angleToX = Math.atan2(direction.y, direction.x);
let heading = Cesium.Math.toDegrees(angleToX);
可以看出,两种方法就是计算localVector的方式不同,结果是一致的。
1、红线为以1为原点建立的相对坐标系的x轴正方向。
2、Math.atan2是内置方法