第一次提交
This commit is contained in:
@@ -0,0 +1,163 @@
|
||||
// Copyright 2025 https://yuewu.dev/en All Rights Reserved.
|
||||
|
||||
#pragma once
|
||||
|
||||
#include "Kismet/BlueprintFunctionLibrary.h"
|
||||
#include "GMS_Vector.generated.h"
|
||||
|
||||
UCLASS(Meta = (BlueprintThreadSafe))
|
||||
class GENERICMOVEMENTSYSTEM_API UGMS_Vector : public UBlueprintFunctionLibrary
|
||||
{
|
||||
GENERATED_BODY()
|
||||
|
||||
public:
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (AutoCreateRefTerm = "Vector", ReturnDisplayName = "Vector"))
|
||||
static FVector ClampMagnitude01(const FVector& Vector);
|
||||
|
||||
static FVector3f ClampMagnitude01(const FVector3f& Vector);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", DisplayName = "Clamp Magnitude 01 2D",
|
||||
Meta = (AutoCreateRefTerm = "Vector", ReturnDisplayName = "Vector"))
|
||||
static FVector2D ClampMagnitude012D(const FVector2D& Vector);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (ReturnDisplayName = "Direction"))
|
||||
static FVector2D RadianToDirection(float Radian);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (ReturnDisplayName = "Direction"))
|
||||
static FVector RadianToDirectionXY(float Radian);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (ReturnDisplayName = "Direction"))
|
||||
static FVector2D AngleToDirection(float Angle);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (ReturnDisplayName = "Direction"))
|
||||
static FVector AngleToDirectionXY(float Angle);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (AutoCreateRefTerm = "Direction", ReturnDisplayName = "Angle"))
|
||||
static double DirectionToAngle(const FVector2D& Direction);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (AutoCreateRefTerm = "Direction", ReturnDisplayName = "Angle"))
|
||||
static double DirectionToAngleXY(const FVector& Direction);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (AutoCreateRefTerm = "Vector", ReturnDisplayName = "Vector"))
|
||||
static FVector PerpendicularClockwiseXY(const FVector& Vector);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (AutoCreateRefTerm = "Vector", ReturnDisplayName = "Vector"))
|
||||
static FVector PerpendicularCounterClockwiseXY(const FVector& Vector);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", DisplayName = "Angle Between (Skip Normalization)",
|
||||
Meta = (AutoCreateRefTerm = "From, To", ReturnDisplayName = "Angle"))
|
||||
static double AngleBetweenSkipNormalization(const FVector& From, const FVector& To);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", Meta = (AutoCreateRefTerm = "From, To", ReturnDisplayName = "Angle"))
|
||||
static float AngleBetweenSignedXY(const FVector3f& From, const FVector3f& To);
|
||||
|
||||
UFUNCTION(BlueprintCallable, BlueprintPure, Category = "GMS|Vector Utility", DisplayName = "Slerp (Skip Normalization)",
|
||||
Meta = (AutoCreateRefTerm = "From, To", ReturnDisplayName = "Direction"))
|
||||
static FVector SlerpSkipNormalization(const FVector& From, const FVector& To, float Ratio);
|
||||
};
|
||||
|
||||
inline FVector UGMS_Vector::ClampMagnitude01(const FVector& Vector)
|
||||
{
|
||||
const auto MagnitudeSquared{Vector.SizeSquared()};
|
||||
|
||||
if (MagnitudeSquared <= 1.0f)
|
||||
{
|
||||
return Vector;
|
||||
}
|
||||
|
||||
const auto Scale{FMath::InvSqrt(MagnitudeSquared)};
|
||||
|
||||
return {Vector.X * Scale, Vector.Y * Scale, Vector.Z * Scale};
|
||||
}
|
||||
|
||||
inline FVector3f UGMS_Vector::ClampMagnitude01(const FVector3f& Vector)
|
||||
{
|
||||
const auto MagnitudeSquared{Vector.SizeSquared()};
|
||||
|
||||
if (MagnitudeSquared <= 1.0f)
|
||||
{
|
||||
return Vector;
|
||||
}
|
||||
|
||||
const auto Scale{FMath::InvSqrt(MagnitudeSquared)};
|
||||
|
||||
return {Vector.X * Scale, Vector.Y * Scale, Vector.Z * Scale};
|
||||
}
|
||||
|
||||
inline FVector2D UGMS_Vector::ClampMagnitude012D(const FVector2D& Vector)
|
||||
{
|
||||
const auto MagnitudeSquared{Vector.SizeSquared()};
|
||||
|
||||
if (MagnitudeSquared <= 1.0f)
|
||||
{
|
||||
return Vector;
|
||||
}
|
||||
|
||||
const auto Scale{FMath::InvSqrt(MagnitudeSquared)};
|
||||
|
||||
return {Vector.X * Scale, Vector.Y * Scale};
|
||||
}
|
||||
|
||||
inline FVector2D UGMS_Vector::RadianToDirection(const float Radian)
|
||||
{
|
||||
float Sin, Cos;
|
||||
FMath::SinCos(&Sin, &Cos, Radian);
|
||||
|
||||
return {Cos, Sin};
|
||||
}
|
||||
|
||||
inline FVector UGMS_Vector::RadianToDirectionXY(const float Radian)
|
||||
{
|
||||
float Sin, Cos;
|
||||
FMath::SinCos(&Sin, &Cos, Radian);
|
||||
|
||||
return {Cos, Sin, 0.0f};
|
||||
}
|
||||
|
||||
inline FVector2D UGMS_Vector::AngleToDirection(const float Angle)
|
||||
{
|
||||
return RadianToDirection(FMath::DegreesToRadians(Angle));
|
||||
}
|
||||
|
||||
inline FVector UGMS_Vector::AngleToDirectionXY(const float Angle)
|
||||
{
|
||||
return RadianToDirectionXY(FMath::DegreesToRadians(Angle));
|
||||
}
|
||||
|
||||
inline double UGMS_Vector::DirectionToAngle(const FVector2D& Direction)
|
||||
{
|
||||
return FMath::RadiansToDegrees(FMath::Atan2(Direction.Y, Direction.X));
|
||||
}
|
||||
|
||||
inline double UGMS_Vector::DirectionToAngleXY(const FVector& Direction)
|
||||
{
|
||||
return FMath::RadiansToDegrees(FMath::Atan2(Direction.Y, Direction.X));
|
||||
}
|
||||
|
||||
inline FVector UGMS_Vector::PerpendicularClockwiseXY(const FVector& Vector)
|
||||
{
|
||||
return {Vector.Y, -Vector.X, Vector.Z};
|
||||
}
|
||||
|
||||
inline FVector UGMS_Vector::PerpendicularCounterClockwiseXY(const FVector& Vector)
|
||||
{
|
||||
return {-Vector.Y, Vector.X, Vector.Z};
|
||||
}
|
||||
|
||||
inline double UGMS_Vector::AngleBetweenSkipNormalization(const FVector& From, const FVector& To)
|
||||
{
|
||||
return FMath::RadiansToDegrees(FMath::Acos(From | To));
|
||||
}
|
||||
|
||||
inline float UGMS_Vector::AngleBetweenSignedXY(const FVector3f& From, const FVector3f& To)
|
||||
{
|
||||
FVector2f FromXY{From};
|
||||
FromXY.Normalize();
|
||||
|
||||
FVector2f ToXY{To};
|
||||
ToXY.Normalize();
|
||||
|
||||
// return FMath::RadiansToDegrees(FMath::Atan2(FromXY ^ ToXY, FromXY | ToXY));
|
||||
|
||||
return FMath::RadiansToDegrees(FMath::Acos(FromXY | ToXY)) * FMath::Sign(FromXY ^ ToXY);
|
||||
}
|
||||
Reference in New Issue
Block a user