// Copyright Epic Games, Inc. All Rights Reserved. #pragma once #include "UObject/Field.h" #include "UObject/TextProperty.h" #include "UObject/EnumProperty.h" #if WITH_EDITOR #include "Containers/ContainersFwd.h" #include "Templates/SharedPointerFwd.h" #endif class FProperty; struct FBindingChainElement; struct FStateTreeBindableStructDesc; struct FStateTreePropertyPathIndirection; struct FEdGraphPinType; struct FStateTreeBlueprintPropertyRef; enum class EStateTreePropertyRefType : uint8; namespace UE::StateTree::PropertyRefHelpers { #if WITH_EDITOR STATETREEMODULE_API extern const FName IsRefToArrayName; STATETREEMODULE_API extern const FName CanRefToArrayName; STATETREEMODULE_API extern const FName RefTypeName; /** * @param RefProperty Property of PropertyRef type. * @param SourceProperty Property to check it's type compatibility. * @param PropertyRefAddress Address of PropertyRef * @param SourceAddress Address of checked property value. * @return true if SourceProperty type is compatible with PropertyRef. */ bool STATETREEMODULE_API IsPropertyRefCompatibleWithProperty(const FProperty& RefProperty, const FProperty& SourceProperty, const void* PropertyRefAddress, const void* SourceAddress); /** * @param SourcePropertyPathIndirections Path indirections of the referenced property. * @param SourceStruct Bindable owner of referenced property. * @return true if property can be referenced by PropertyRef. */ bool STATETREEMODULE_API IsPropertyAccessibleForPropertyRef(TConstArrayView SourcePropertyPathIndirections, FStateTreeBindableStructDesc SourceStruct); /** * @param SourceProperty Referenced property. * @param BindingChain Binding chain to referenced property. * @param SourceStruct Bindable owner of referenced property. * @return true if property can be referenced by PropertyRef. */ bool STATETREEMODULE_API IsPropertyAccessibleForPropertyRef(const FProperty& SourceProperty, TConstArrayView BindingChain, FStateTreeBindableStructDesc SourceStruct); /** * @param RefProperty Property of PropertyRef type. * @param PropertyRefAddress Address of PropertyRef. * @return true if PropertyRef is marked as optional. */ bool STATETREEMODULE_API IsPropertyRefMarkedAsOptional(const FProperty& RefProperty, const void* PropertyRefAddress); /** * @param RefProperty Property of PropertyRef type * @return PinTypes for PropertyRef's internal types */ TArray> STATETREEMODULE_API GetPropertyRefInternalTypesAsPins(const FProperty& RefProperty); /** * @param RefProperty Property of PropertyRef type * @param PropertyRefAddress Address of PropertyRef. * @return PinType for PropertyRef's internal type */ FEdGraphPinType STATETREEMODULE_API GetPropertyRefInternalTypeAsPin(const FProperty& RefProperty, const void* PropertyRefAddress); /** * @param InPropertyRef PropertyRef to get internal type from. * @return PinType for Blueprint PropertyRef's internal type */ FEdGraphPinType STATETREEMODULE_API GetBlueprintPropertyRefInternalTypeAsPin(const FStateTreeBlueprintPropertyRef& InPropertyRef); /** * @param PinType Pin to get type from. * @param OutRefType PropertyRef's referenced type. * @param bOutIsArray True if PropertyRef references an array property. * @param OutObjectType Referenced type's specific object. */ void STATETREEMODULE_API GetBlueprintPropertyRefInternalTypeFromPin(const FEdGraphPinType& PinType, EStateTreePropertyRefType& OutRefType, bool& bOutIsArray, UObject*& OutObjectType); #endif /** * @param Property Property to check * @return true if Property is a PropertyRef */ bool STATETREEMODULE_API IsPropertyRef(const FProperty& Property); /** * @param SourceProperty Property to check it's type compatibility. * @param PropertyRefAddress Address of PropertyRef * @return true if SourceProperty type is compatible with Blueprint PropertyRef. */ bool STATETREEMODULE_API IsBlueprintPropertyRefCompatibleWithProperty(const FProperty& SourceProperty, const void* PropertyRefAddress); template struct Validator {}; template<> struct Validator { static bool IsValid(const FProperty& Property) { return true; } }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template<> struct Validator { static bool IsValid(const FProperty& Property){ return Property.IsA(); }; }; template struct Validator, void>::Type> { static bool IsValid(const FProperty& Property) { if (const FArrayProperty* ArrayProperty = CastField(&Property)) { return Validator::IsValid(*ArrayProperty->Inner); } return false; } }; /* Checks if provided property is compatible with selected ScriptStruct. */ bool STATETREEMODULE_API IsPropertyCompatibleWithStruct(const FProperty& Property, const class UScriptStruct& Struct); template struct Validator::Get, void())> { static bool IsValid(const FProperty& Property) { if (const FStructProperty* StructProperty = CastField(&Property)) { return StructProperty->Struct->IsChildOf(TBaseStructure::Get()); } return false; } }; /* Checks if provided property is compatible with selected Class. */ bool STATETREEMODULE_API IsPropertyCompatibleWithClass(const FProperty& Property, const class UClass& Class); template struct Validator::Type, UObject>::IsDerived>::Type> { static bool IsValid(const FProperty& Property) { if (const FObjectProperty* ObjectProperty = CastField(&Property)) { return ObjectProperty->PropertyClass == TRemovePointer::Type::StaticClass(); } return false; } }; /* Checks if provided property is compatible with selected Enum. */ bool STATETREEMODULE_API IsPropertyCompatibleWithEnum(const FProperty& Property, const class UEnum& Enum); template struct Validator::Value>::Type> { static bool IsValid(const FProperty& Property) { if (const FEnumProperty* EnumProperty = CastField(&Property)) { return EnumProperty->GetEnum() == StaticEnum(); } return false; } }; }