7#include "GameFramework/Actor.h"
8#include "Engine/GameViewportClient.h"
9#include "Engine/OverlapResult.h"
10#include "Engine/HitResult.h"
11#include "Engine/EngineTypes.h"
12#include "Engine/Engine.h"
13#include "Engine/World.h"
16#include "DrawDebugHelpers.h"
21 bool ActorPositionWasChanged =
false;
25 return ActorPositionWasChanged;
28 UWorld* World = Actor->GetWorld();
32 const FVector ActorLocation = Actor->GetActorLocation();
33 const FVector StartLocation = ActorLocation + FVector(0.0f, 0.0f, StartZOffset);
34 const FVector EndLocation = ActorLocation - FVector(0.0f, 0.0f, EndZOffset);
36 FCollisionQueryParams QueryParams;
37 QueryParams.AddIgnoredActor(Actor);
38 bool Hits = World->LineTraceSingleByChannel(HitResult, StartLocation, EndLocation, ECC_WorldStatic, QueryParams);
43 Actor->TeleportTo(HitResult.ImpactPoint, Actor->GetActorRotation());
44 ActorPositionWasChanged =
true;
48 return ActorPositionWasChanged;
62 const FVector CurrentActorLocation = Actor->GetActorLocation();
63 const FVector EndActorLocation = CurrentActorLocation + FVector(0.0f, 0.0f, AboveOffset);
64 Actor->TeleportTo(EndActorLocation, Actor->GetActorRotation());
77 UWorld* World = Actor->GetWorld();
81 FTransform
Transform = Actor->GetActorTransform();
82 FVector ActorLocation =
Transform.GetLocation();
83 FVector ActorScale =
Transform.GetScale3D();
86 FVector MeshExtent = Mesh->GetBounds().BoxExtent;
87 FVector TopExtent = FVector(MeshExtent.X, MeshExtent.Y, MeshExtent.Z * TopPercentage);
89 FVector StartLocation = ActorLocation + FVector(0.0f, 0.0f, MeshExtent.Z);
90 FVector EndLocation = ActorLocation + FVector(0.0f, 0.0f, MeshExtent.Z * TopPercentage);
93 FCollisionQueryParams QueryParams;
94 QueryParams.AddIgnoredActor(Actor);
97 return World->LineTraceSingleByChannel(HitResult, StartLocation, EndLocation, CollisionChannel, QueryParams);
108 UE_LOG(LogTemp, Warning, TEXT(
"UPhysicsUtilities.cpp: StaticMesh is null!"));
113 if (!GEngine || !GEngine->GameViewport)
118 TArray<FOverlapResult> OverlapResults;
120 UWorld* World = GEngine->GameViewport->GetWorld();
123 FVector Location =
Transform.GetLocation();
124 FQuat Rotation =
Transform.GetRotation();
126 FBox ActorBounds = StaticMesh->GetBoundingBox().TransformBy(FTransform(Rotation, Location, Scale));
128 World->OverlapMultiByObjectType(
132 FCollisionObjectQueryParams(ECC_WorldStatic),
133 FCollisionShape::MakeBox(ActorBounds.GetSize() * 0.5f)
137 return OverlapResults.Num() > 0;
142 return FindOverlappingActorsOfClass<AActor>(ActorTransform, Radius, DebugVisualizeRadius);
147 if (!GEngine || !GEngine->GameViewport)
152 UWorld* World = GEngine->GameViewport->GetWorld();
158 FVector Position = InTransform.GetLocation();
159 const float HeightAboveGroundMeters = Position.Z;
162 const FVector TraceStart = FVector(Position.X, Position.Y, 6000.0f);
163 const FVector TraceEnd = TraceStart - FVector(0, 0, 100000.0f);
165 FHitResult HitResult;
166 FCollisionQueryParams QueryParams;
167 QueryParams.AddIgnoredActor(Actor);
169 bool bHit = World->LineTraceSingleByChannel(HitResult, TraceStart, TraceEnd, ECC_GameTraceChannel6, QueryParams);
172 Position.Z = HitResult.ImpactPoint.Z + (HeightAboveGroundMeters * 100.0f);
173 InTransform.SetLocation(Position);
184 TArray<T*> OverlappingActors;
186 if (!GEngine || !GEngine->GameViewport)
188 return OverlappingActors;
191 UWorld* World = GEngine->GameViewport->GetWorld();
195 TArray<FOverlapResult> OverlapResults;
196 FCollisionQueryParams Params;
197 Params.AddIgnoredActor(
nullptr);
198 Params.bTraceComplex =
false;
199 Params.bReturnPhysicalMaterial =
false;
201 FCollisionObjectQueryParams ObjectQueryParams;
202 ObjectQueryParams.AddObjectTypesToQuery(ECC_WorldStatic);
204 bool bOverlap = World->OverlapMultiByObjectType(
206 ActorTransform.GetLocation(),
207 ActorTransform.GetRotation(),
209 FCollisionShape::MakeSphere(Radius),
215 for (
const FOverlapResult& OverlapResult : OverlapResults)
217 T* OverlappingActor = Cast<T>(OverlapResult.GetActor());
218 if (OverlappingActor)
220 OverlappingActors.Add(OverlappingActor);
227 if (DebugVisualizeRadius)
229 DrawDebugSphere(World, ActorTransform.GetLocation(), Radius, 12, FColor::Green,
false, 2.0f, 0, 1.0f);
233 return OverlappingActors;
static bool SnapActorAboveGround(AActor *Actor, float AboveOffset=50.0f)
static bool HasOverlappingActors(const UStaticMesh *StaticMesh, const FTransform &Transform)
static bool AlignTransformFromGroundInMeters(AActor *Actor, FTransform &InTransform)
static bool DoesTopPercentageMeshOverlap(AActor *Actor, const UStaticMesh *Mesh, float TopPercentage, ECollisionChannel CollisionChannel)
static TArray< T * > FindOverlappingActorsOfClass(const FTransform &ActorTransform, float Radius, bool DebugVisualizeRadius=false)
static TArray< AActor * > FindOverlappingActorsInSphere(const FTransform &ActorTransform, float Radius, bool DebugVisualizeRadius=false)
static bool SnapActorToGround(AActor *Actor, float StartZOffset=600.0f, float EndZOffset=600.0f)