.h
// Fill out your copyright notice in the Description page of Project Settings.
#pragma once
#include "CoreMinimal.h"
#include "GameFramework/Actor.h"
#include "SplineTraceActor.generated.h"
UCLASS()
class MZEDUCATION_API ASplineTraceActor : public AActor
{
GENERATED_BODY()
public:
// Sets default values for this actor's properties
ASplineTraceActor();
protected:
// Called when the game starts or when spawned
virtual void BeginPlay() override;
public:
// Called every frame
virtual void Tick(float DeltaTime) override;
public:
//根组件;
UPROPERTY(VisibleDefaultsOnly, BlueprintReadWrite, Category = "DefaultComponent")
class USceneComponent* Root;
//可编辑的Spline;
UPROPERTY(VisibleDefaultsOnly, BlueprintReadWrite, Category = "DefaultComponent")
class USplineComponent* EditableSpline;
//用于显示的Spline;
UPROPERTY(VisibleDefaultsOnly, BlueprintReadWrite, Category = "DefaultComponent")
class USplineComponent* DisplaybleSpline;
//用于存放生成的点的信息的数组;
UPROPERTY(EditAnywhere,BlueprintReadWrite,Category="DefaultValues")
TArray Points;
//分割次数 点的密集程度
UPROPERTY(EditAnywhere, BlueprintReadWrite, Category = "DefaultValues", meta = (ClampMin = "10", ClampMax = "45"))
int Times=10;
//函数序列
//ConstructionScript函数;
UFUNCTION(BlueprintCallable, Category = "ConstructionFunction")
virtual void OnConstruction(const FTransform& Transform) override;
//得到分割后每段的距离;
UFUNCTION(BlueprintCallable, Category = "CaculateDistance")
float GetPerDistance();
//得到发出射线的点的起始点和终止点
UFUNCTION(BlueprintCallable, Category = "CaculateDistance")
void GetTracePoint(float CurrentDistance, FVector& StartPointLoc, FVector& EndPointLoc);
};
.cpp
// Fill out your copyright notice in the Description page of Project Settings.
#include "SplineTraceActor.h"
#include "Components/SplineComponent.h"
#include "Engine/EngineTypes.h"
#include "Engine/World.h"
#include "Components/TimelineComponent.h"
// Sets default values
ASplineTraceActor::ASplineTraceActor()
{
// Set this actor to call Tick() every frame. You can turn this off to improve performance if you don't need it.
PrimaryActorTick.bCanEverTick = true;
Root = CreateDefaultSubobject(TEXT("RootCom"));
EditableSpline = CreateDefaultSubobject(TEXT("EditableSpline"));
DisplaybleSpline = CreateDefaultSubobject(TEXT("DisplaybleSpline"));
EditableSpline->bInputSplinePointsToConstructionScript = true;
DisplaybleSpline->bInputSplinePointsToConstructionScript = true;
RootComponent = Root;
EditableSpline->SetupAttachment(Root);
DisplaybleSpline->SetupAttachment(Root);
DisplaybleSpline->ClearSplinePoints(true);
}
// Called when the game starts or when spawned
void ASplineTraceActor::BeginPlay()
{
Super::BeginPlay();
}
// Called every frame
void ASplineTraceActor::Tick(float DeltaTime)
{
Super::Tick(DeltaTime);
}
void ASplineTraceActor::OnConstruction(const FTransform& Transform)
{
Super::OnConstruction(Transform);
Points.Empty();
for (int i=0;iLineTraceSingleByObjectType(hitresult, StartPoint, EndPoint, true);
FVector Hitpoint = hitresult.Location;
Points.Add(Hitpoint);
}
}
DisplaybleSpline->ClearSplinePoints(true);
for (int i=0;iAddSplineWorldPoint(Points[i]);
//UE_LOG(LogTemp, Warning, TEXT("Construction函数,points:%d,points个数:%d"),Points[i].Y,Points.Num());
}
}
float ASplineTraceActor::GetPerDistance()
{
float perDistance = 0;
if (Times)
{
perDistance = (EditableSpline->GetSplineLength())/Times;
//UE_LOG(LogTemp, Warning, TEXT("%f:"), perDistance)
}
else
{
UE_LOG(LogTemp,Warning,TEXT("Times的值为空!"))
}
return perDistance;
}
void ASplineTraceActor::GetTracePoint(float CurrentDistance, FVector& StartPointLoc, FVector& EndPointLoc)
{
FVector Point = EditableSpline->GetLocationAtDistanceAlongSpline(CurrentDistance, ESplineCoordinateSpace::Local);
Point = FVector(Point.X, Point.Y, Point.Z + 1000);
StartPointLoc = GetActorLocation() + GetActorRotation().RotateVector(Point);
EndPointLoc = StartPointLoc + FVector(0, 0, -3000);
}