14#include "Engine/CollisionProfile.h"
15#include "DrawDebugHelpers.h"
19 return (SplineComponent !=
nullptr) &&
20 (SplineComponent->GetNumberOfSplinePoints() > 1);
25 auto *
Vehicle = (Actor->IsPendingKill() ? nullptr : Cast<ACarlaWheeledVehicle>(Actor));
27 Cast<AWheeledVehicleAIController>(
Vehicle->GetController()) :
33 const TArray<USplineComponent *> &Routes,
34 const TArray<float> &Probabilities)
36 check(Routes.Num() > 0);
38 if (Routes.Num() == 1)
44 check((Index >= 0) && (Index < Routes.Num()));
49 : Super(ObjectInitializer)
52 ObjectInitializer.CreateDefaultSubobject<USceneComponent>(
this, TEXT(
"SceneRootComponent"));
53 RootComponent->SetMobility(EComponentMobility::Static);
55 TriggerVolume = CreateDefaultSubobject<UBoxComponent>(TEXT(
"TriggerVolume"));
69 Super::BeginDestroy();
73void ARoutePlanner::PostEditChangeProperty(FPropertyChangedEvent &PropertyChangedEvent)
75 Super::PostEditChangeProperty(PropertyChangedEvent);
76 const auto Size =
Routes.Num();
77 if (PropertyChangedEvent.Property && (Size !=
Probabilities.Num()))
80 for (
auto i = 0; i < Size; ++i)
85 Routes[i] = NewObject<USplineComponent>(
this);
86 Routes[i]->SetupAttachment(RootComponent);
87 Routes[i]->SetHiddenInGame(
true);
88 Routes[i]->SetMobility(EComponentMobility::Static);
89 Routes[i]->RegisterComponent();
98 USplineComponent *NewSpline = NewObject<USplineComponent>(
this);
99 NewSpline->bHiddenInGame =
true;
102 NewSpline->EditorUnselectedSplineSegmentColor = FLinearColor(1.f, 0.15f, 0.15f);
105 NewSpline->SetLocationAtSplinePoint(0, routePoints[0], ESplineCoordinateSpace::World,
true);
106 NewSpline->SetLocationAtSplinePoint(1, routePoints[1], ESplineCoordinateSpace::World,
true);
108 for (
int i = 2; i < routePoints.Num(); ++i)
110 NewSpline->AddSplinePoint(routePoints[i], ESplineCoordinateSpace::World,
true);
125 if (!Controller.IsPendingKill() && (Controller.
GetRandomEngine() !=
nullptr))
130 TArray<FVector> WayPoints;
131 const auto Size = Route->GetNumberOfSplinePoints();
134 WayPoints.Reserve(Size);
135 for (
auto i = 1; i < Size; ++i)
137 WayPoints.Add(Route->GetLocationAtSplinePoint(i, ESplineCoordinateSpace::World));
144 UE_LOG(LogCarla, Error, TEXT(
"ARoutePlanner '%s' has a route with zero way-points."), *GetName());
154 UE_LOG(LogCarla, Warning, TEXT(
"ARoutePlanner '%s' has no route assigned."), *GetName());
158 for (
auto &&Route :
Routes)
162 UE_LOG(LogCarla, Error, TEXT(
"ARoutePlanner '%s' has a route with zero way-points."), *GetName());
188 Super::EndPlay(EndPlayReason);
200 if (Controller !=
nullptr)
209 for (
int i = 0, lenRoutes =
Routes.Num(); i < lenRoutes; ++i)
211 for (
int j = 0, lenNumPoints =
Routes[i]->GetNumberOfSplinePoints() - 1; j < lenNumPoints; ++j)
213 const FVector p0 =
Routes[i]->GetLocationAtSplinePoint(j + 0, ESplineCoordinateSpace::World);
214 const FVector p1 =
Routes[i]->GetLocationAtSplinePoint(j + 1, ESplineCoordinateSpace::World);
216 static const float MinThickness = 3.f;
217 static const float MaxThickness = 15.f;
219 const float Dist = (float) j / (
float) lenNumPoints;
220 const float OneMinusDist = 1.f - Dist;
221 const float Thickness = OneMinusDist * MaxThickness + MinThickness;
227 GetWorld(), p0, p1, FColor(0, 0, 255 * OneMinusDist),
228 true, -1.f, 0, Thickness);
234 GetWorld(), p0, p1, FColor(0, 255 * OneMinusDist, 0),
235 true, -1.f, 0, Thickness);
static AWheeledVehicleAIController * GetVehicleController(AActor *Actor)
static bool IsSplineValid(const USplineComponent *SplineComponent)
static const USplineComponent * PickARoute(URandomEngine &RandomEngine, const TArray< USplineComponent * > &Routes, const TArray< float > &Probabilities)
virtual void BeginPlay() override
virtual void BeginDestroy() override
void AddRoute(float probability, const TArray< FVector > &routePoints)
UBoxComponent * TriggerVolume
ARoutePlanner(const FObjectInitializer &ObjectInitializer)
void AssignRandomRoute(AWheeledVehicleAIController &Controller) const
void OnTriggerBeginOverlap(UPrimitiveComponent *OverlappedComp, AActor *OtherActor, UPrimitiveComponent *OtherComp, int32 OtherBodyIndex, bool bFromSweep, const FHitResult &SweepResult)
TArray< USplineComponent * > Routes
TArray< float > Probabilities
virtual void EndPlay(EEndPlayReason::Type EndPlayReason) override
Wheeled vehicle controller with optional AI.
URandomEngine * GetRandomEngine()
void SetFixedRoute(const TArray< FVector > &Locations, bool bOverwriteCurrent=true)
Set a fixed route to follow if autopilot is enabled.
int32 GetIntWithWeight(const TArray< float > &Weights)