一.方法一:需要一个Actor里,向下垂直射线。自身高度-射线距离。
#include "CesiumGlobeAnchorComponent.h"
#include "CesiumOriginShiftComponent.h"
#include "GeoTransforms.h"
#include "CesiumGeoreference.h"
UPROPERTY(BlueprintReadOnly, EditAnywhere, meta = (AllowPrivateAccess = "true"))
UCesiumGlobeAnchorComponent* globeAnchor;//地球组件
UPROPERTY(BlueprintReadOnly, EditAnywhere, meta = (AllowPrivateAccess = "true"))
UCesiumOriginShiftComponent* originShift;//地球组件
UWorld* world;
FHitResult hitRes;
ECollisionChannel colChannel;
GeoTransforms* geoTrans;
ACesiumGeoreference* Geo;
核心逻辑如下,Pitch为-90.,俯仰向下。射线从自身射到 自身前方50000000cm,返回的FHitResult里面可以拿到距离。自身的高度-距离就是地面高度。
if (globeAnchor != nullptr) {
if ((!isnan(Latitude)) && (!isnan(Longitude)))
{
globeAnchor->MoveToLongitudeLatitudeHeight(FVector(Longitude, Latitude, Atitude));
//FVector actorLoc = globeAnchor->GetLongitudeLatitudeHeight();
FVector actorLoc = GetActorLocation();
globeAnchor->SetEastSouthUpif (globeAnchor != nullptr) {
if ((!isnan(Latitude)) && (!isnan(Longitude)))
{
globeAnchor->MoveToLongitudeLatitudeHeight(FVector(Longitude, Latitude, Atitude));
//FVector actorLoc = globeAnchor->GetLongitudeLatitudeHeight();
FVector actorLoc = GetActorLocation();
globeAnchor->SetEastSouthUpRotation(FRotator(-90, 0 - 90, 0).Quaternion());
bool isSuccess = world->LineTraceSingleByChannel(hitRes, actorLoc, actorLoc + GetActorForwardVector() * 50000000, colChannel);
// 绘制射线
DrawDebugLine(GetWorld(), actorLoc, hitRes.GetActor() ? hitRes.Location : actorLoc + GetActorForwardVector() * 50000000, FColor::Red, false, 1.0f);
//GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Green, actorLoc.ToString());
//GEngine->AddOnScreenDebugMessage(-1,10.0f,FColor::Red, GetActorForwardVector().ToString());
/*if (Geo->IsValidLowLevel())
{*/
//float z = Geo->TransformLongitudeLatitudeHeightPositionToUnreal(hitRes.Location).Z;
float z = Atitude-(hitRes.Distance/100);
//GEngine->AddOnScreenDebugMessage(-1, 10.0f, FColor::Red, FString::Printf(TEXT("%f"), z));
return z;
/* }*/
}Rotation(FRotator(-90, 0 - 90, 0).Quaternion());
bool isSuccess = world->LineTraceSingleByChannel(hitRes, actorLoc, actorLoc + GetActorForwardVector() * 50000000, colChannel);
// 绘制射线
DrawDebugLine(GetWorld(), actorLoc, hitRes.GetActor() ? hitRes.Location : actorLoc + GetActorForwardVector() * 50000000, FColor::Red, false, 1.0f);
//GEngine->AddOnScreenDebugMessage(-1, 10.f, FColor::Green, actorLoc.ToString());
//GEngine->AddOnScreenDebugMessage(-1,10.0f,FColor::Red, GetActorForwardVector().ToString());
/*if (Geo->IsValidLowLevel())
{*/
//float z = Geo->TransformLongitudeLatitudeHeightPositionToUnreal(hitRes.Location).Z;
float z = Atitude-(hitRes.Distance/100);
//GEngine->AddOnScreenDebugMessage(-1, 10.0f, FColor::Red, FString::Printf(TEXT("%f"), z));
return z;
/* }*/
}
方法二. 在某个目标,上空射线得到位置。UE位置坐标系 再通过CesiumGereforce组件转化 为经纬度坐标系代码如下:。UE5的TransformLongitudeLatitudeHeightPositionToUnreal的支持double,UE4蓝图只支持float的可能需要改一下Cesium源码,UE4从零开始制作数字孪生道路监测平台_ue4数字孪生-CSDN博客。
float AAltitudeChecker::GetAltitudeByLongitudeAndLatitude(const float& Longitude, const float& Latitude) {
FVector actorLoc = GetActorLocation();
//SetActorRotation(FRotator(-90, 0, 0));
if (globeAnchor) {
globeAnchor->MoveToLongitudeLatitudeHeight(FVector( Longitude, Latitude, 10000.f ));
globeAnchor->SetEastSouthUpRotation(FRotator(-90, 0, 0).Quaternion());
bool isSuccess = world->LineTraceSingleByChannel(hitRes, actorLoc, actorLoc + GetActorForwardVector() * 50000000, colChannel);
if (isSuccess) {
float floatRes = GetUEABsByLLA(hitRes.Location).Z;
return floatRes;
}
}
return -1;
}
FVector AAltitudeChecker::GetUEABsByLLA(const FVector& lla) {
if(Geo->IsValidLowLevel()) return Geo->TransformLongitudeLatitudeHeightPositionToUnreal(FVector(lla.X, lla.Y, lla.Z));
return FVector();
}