UE4中贝塞尔曲线的简单实现
最近研究了下贝塞尔曲线的原理,闲着无事就在UE4里面做了一下,效果还不错,给大家分享出来.
首先我们都知道贝塞尔曲线计算公式是不断递归找到对应的曲线点.
话不多说,直接上代码.
我们先在UE4创建一个C++的Actor类.
然后我们开始吧.
前文提示,在看下列代码前请先了解下贝塞尔曲线的原理和计算方法,不然会看懵逼!
//头文件
// Fill out your copyright notice in the Description page of Project Settings.
#pragma once
#include "CoreMinimal.h"
#include "GameFramework/Actor.h"
#include "Berzier.generated.h"
UCLASS()
class TCPSERVER_API ABerzier : public AActor
{
GENERATED_BODY()
public:
// Sets default values for this actor's properties
ABerzier();
protected:
// Called when the game starts or when spawned
virtual void BeginPlay() override;
public:
// Called every frame
virtual void Tick(float DeltaTime) override;
//我们的贝塞尔曲线函数
UFUNCTION(BlueprintCallable)
TArray<FVector2D> BerzierCurve(TArray<FVector2D> src);
};
// Fill out your copyright notice in the Description page of Project Settings.
#include "Berzier.h"
// Sets default values
ABerzier::ABerzier()
{
// 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 ;
}
// Called when the game starts or when spawned
void ABerzier::BeginPlay()
{
Super :: BeginPlay() ;
}
// Called every frame
void ABerzier::Tick(float DeltaTime)
{
Super :: Tick(DeltaTime) ;
}
TArray<FVector2D> ABerzier::BerzierCurve(TArray<FVector2D> src)
{
//不存在1阶
if ( src.Num()<1 )
{
return src ;
}
//-----------------------------t的分布步数------------------------------------
const float step = 0.01 ;
//---------------------------------------------------------------------------
// -----------------------------返回值-----------------------------------------
TArray<FVector2D> res ;
// ----------------------------------------------------------------------------
// ---------------------------2阶 一条直线------------------------------------
if ( src .Num()==1 )
{
for (float t=0 ; t<1 ; t+=step)
{
res.Add(src[0]) ;
}
return res ;
}
// --------------------------------------------------------------------------
//-----------------------------------3阶 及以上-----------------------------------------
//---------------------------src1是起点到最后一个点的上一个点-----------------------------
TArray<FVector2D> src1 ;
//-------------------------------------------------------------------------------------
//---------------------------src2是从第二个点到最后一个点---------------------------------
TArray<FVector2D> src2 ;
//--------------------------------------------------------------------------------------
//---------------------------对src1,src2赋值 --------------------------------------------
for (int32 i=0;i<src.Num()-1;i++)
{
src1 .Add(src[i]) ;
UE_LOG(LogTemp, Warning, TEXT("==%s\t"),*src1[i].ToString());
}
for (int32 j = 0; j < src.Num(); j++)
{
src2 .Add(src[j]) ;
UE_LOG(LogTemp, Warning, TEXT("==%s\t"), *src2[j].ToString());
}
src2 .RemoveAt(0) ;
//---------------------------------------------------------------------------------------
//----------------------------递归调用所有的点--------------------------------------------
TArray<FVector2D> pln1=BerzierCurve(src1) ;
TArray<FVector2D> pln2=BerzierCurve(src2) ;
//---------------------------------------------------------------------------------------
for (float t=0;t<1;t+=step)
{
FVector2D tmp ;
//-------------------------------------应用贝塞尔曲线算法------------------------------
tmp = (
(1.0 - t)
*
pln1[FMath::RoundToInt(1.0 / step * t)]
)
+ (
t
*
pln2[FMath::RoundToInt(1.0 / step * t)]
) ;
//------------------------------------------------------------------------------------
//--------------------最终得到的点就是贝塞尔曲线上的点的位置了-----------------------
res . Add (tmp) ;
//--------------------------------------------------------------------------------
}
return res ;
//-----------------------------------------------------------------------------------
}
完成后我们转到蓝图:
派生一个从我们上面这个类的子类.然后打开构造函数,我们开始!
然后我们开始写蓝图
然后就可以查看效果了
大家自己试试吧
https://www.bilibili.com/video/BV17f4y1h7sm 这是我的B站视频演示链接.
好了,今天的分享到此为止了,等我下次再分享一波.曲率的计算方式.可以随心所欲的生成不同的曲线.有了结果会第一时间发在b站