2021-09-28 13:33:00 -04:00
// Copyright Epic Games, Inc. All Rights Reserved.
# pragma once
# include "SmartObjectTypes.h"
2021-11-26 15:48:13 -05:00
# include "SmartObjectDefinition.h"
2021-09-28 13:33:00 -04:00
# include "SmartObjectRuntime.generated.h"
2023-01-18 10:52:51 -05:00
class USmartObjectComponent ;
2023-11-29 11:23:11 -05:00
namespace UE : : SmartObject
{
uint16 GetMaskForEnabledReasonTag ( const FGameplayTag Tag ) ;
}
2022-03-16 03:47:02 -04:00
/** Delegate fired when a given tag is added or removed. Tags on smart object are not using reference counting so count will be 0 or 1 */
2023-01-18 10:52:51 -05:00
UE_DEPRECATED ( 5.2 , " Tag changes are now broadcasted using FOnSmartObjectEvent. " )
2022-03-16 03:47:02 -04:00
DECLARE_DELEGATE_TwoParams ( FOnSmartObjectTagChanged , const FGameplayTag , int32 ) ;
2021-09-28 13:33:00 -04:00
/**
* Enumeration to represent the runtime state of a slot
*/
UENUM ( )
enum class ESmartObjectSlotState : uint8
{
2022-01-19 14:16:16 -05:00
Invalid ,
2022-03-16 03:47:02 -04:00
/** Slot is available */
2021-09-28 13:33:00 -04:00
Free ,
2022-03-16 03:47:02 -04:00
/** Slot is claimed but interaction is not active yet */
2021-09-28 13:33:00 -04:00
Claimed ,
2022-03-16 03:47:02 -04:00
/** Slot is claimed and interaction is active */
Occupied ,
/** Slot can no longer be claimed or used since the parent object and its slot are disabled (e.g. instance tags) */
2022-11-01 15:11:25 -04:00
Disabled UE_DEPRECATED ( 5.2 , " Use IsEnabled() instead. " ) ,
2021-09-28 13:33:00 -04:00
} ;
2024-02-08 13:21:26 -05:00
/**
* Indicates if the subsystem should try to spawn the actor associated to the smartobject
* if it is currently owned by an instanced actor .
*/
UENUM ( )
enum class ETrySpawnActorIfDehydrated : uint8
{
No ,
Yes
} ;
2021-09-28 13:33:00 -04:00
/**
* Struct describing a reservation between a user and a smart object slot .
*/
2021-11-26 15:48:13 -05:00
USTRUCT ( BlueprintType )
2021-09-28 13:33:00 -04:00
struct SMARTOBJECTSMODULE_API FSmartObjectClaimHandle
{
GENERATED_BODY ( )
2022-01-19 14:16:16 -05:00
FSmartObjectClaimHandle ( const FSmartObjectHandle InSmartObjectHandle , const FSmartObjectSlotHandle InSlotHandle , const FSmartObjectUserHandle & InUser )
: SmartObjectHandle ( InSmartObjectHandle ) , SlotHandle ( InSlotHandle ) , UserHandle ( InUser )
2021-09-28 13:33:00 -04:00
{ }
FSmartObjectClaimHandle ( )
{ }
bool operator = = ( const FSmartObjectClaimHandle & Other ) const
{
2022-03-18 12:31:49 -04:00
return SmartObjectHandle = = Other . SmartObjectHandle
2022-01-19 14:16:16 -05:00
& & SlotHandle = = Other . SlotHandle
& & UserHandle = = Other . UserHandle ;
2021-09-28 13:33:00 -04:00
}
2021-11-26 15:48:13 -05:00
bool operator ! = ( const FSmartObjectClaimHandle & Other ) const
{
return ! ( * this = = Other ) ;
}
2022-01-19 14:16:16 -05:00
friend FString LexToString ( const FSmartObjectClaimHandle & Handle )
2021-09-28 13:33:00 -04:00
{
2022-01-19 14:16:16 -05:00
return FString : : Printf ( TEXT ( " Object:%s Slot:%s User:%s " ) , * LexToString ( Handle . SmartObjectHandle ) , * LexToString ( Handle . SlotHandle ) , * LexToString ( Handle . UserHandle ) ) ;
2021-09-28 13:33:00 -04:00
}
void Invalidate ( ) { * this = InvalidHandle ; }
2022-03-16 03:47:02 -04:00
/**
2022-03-18 12:31:49 -04:00
* Indicates that the handle was properly assigned by a call to ' Claim ' but doesn ' t guarantee that the associated
* object and slot are still registered in the simulation .
* This information requires a call to ` USmartObjectSubsystem : : IsClaimedObjectValid ` using the handle .
2022-03-16 03:47:02 -04:00
*/
2021-09-28 13:33:00 -04:00
bool IsValid ( ) const
{
2022-01-19 14:16:16 -05:00
return SmartObjectHandle . IsValid ( )
& & SlotHandle . IsValid ( )
& & UserHandle . IsValid ( ) ;
2021-09-28 13:33:00 -04:00
}
static const FSmartObjectClaimHandle InvalidHandle ;
2022-11-01 15:11:25 -04:00
/** Handle to the Smart Object where the claimed slot belongs to. */
2023-08-22 12:17:21 -04:00
UPROPERTY ( BlueprintReadOnly , EditAnywhere , Transient , Category = " Default " )
2022-01-19 14:16:16 -05:00
FSmartObjectHandle SmartObjectHandle ;
2021-09-28 13:33:00 -04:00
2022-11-01 15:11:25 -04:00
/** Handle of the claimed slot. */
2023-08-22 12:17:21 -04:00
UPROPERTY ( BlueprintReadOnly , EditAnywhere , Transient , Category = " Default " )
2022-01-19 14:16:16 -05:00
FSmartObjectSlotHandle SlotHandle ;
2021-09-28 13:33:00 -04:00
2022-11-01 15:11:25 -04:00
/** Handle describing the user which claimed the slot. */
UPROPERTY ( EditAnywhere , Transient , Category = " Default " )
2022-01-19 14:16:16 -05:00
FSmartObjectUserHandle UserHandle ;
} ;
/**
* Runtime data holding the final slot transform ( i . e . parent transform applied on slot local offset and rotation )
*/
USTRUCT ( )
2023-07-18 08:42:51 -04:00
struct UE_DEPRECATED ( 5.3 , " Transform is moved to FSmartObjectRuntimeSlot. " ) SMARTOBJECTSMODULE_API FSmartObjectSlotTransform : public FSmartObjectSlotStateData
2022-01-19 14:16:16 -05:00
{
GENERATED_BODY ( )
const FTransform & GetTransform ( ) const { return Transform ; }
FTransform & GetMutableTransform ( ) { return Transform ; }
void SetTransform ( const FTransform & InTransform ) { Transform = InTransform ; }
protected :
UPROPERTY ( Transient )
FTransform Transform ;
2021-09-28 13:33:00 -04:00
} ;
/** Delegate to notify when a given slot gets invalidated and the interaction must be aborted */
DECLARE_DELEGATE_TwoParams ( FOnSlotInvalidated , const FSmartObjectClaimHandle & , ESmartObjectSlotState /* Current State */ ) ;
/**
2021-11-26 15:48:13 -05:00
* Struct to store and manage state of a runtime instance associated to a given slot definition
2021-09-28 13:33:00 -04:00
*/
2022-11-01 15:11:25 -04:00
2021-09-28 13:33:00 -04:00
USTRUCT ( )
2022-11-01 15:11:25 -04:00
struct FSmartObjectRuntimeSlot
2021-09-28 13:33:00 -04:00
{
GENERATED_BODY ( )
public :
2022-01-19 14:16:16 -05:00
/* Provide default constructor to be able to compile template instantiation 'UScriptStruct::TCppStructOps<FSmartObjectSlotState>' */
/* Also public to pass void 'UScriptStruct::TCppStructOps<FSmartObjectSlotState>::ConstructForTests(void *)' */
2023-01-18 10:52:51 -05:00
FSmartObjectRuntimeSlot ( ) : bSlotEnabled ( true ) , bObjectEnabled ( true ) { }
2023-07-18 08:42:51 -04:00
FVector3f GetSlotOffset ( ) const { return Offset ; }
FRotator3f GetSlotRotation ( ) const { return Rotation ; }
FTransform GetSlotLocalTransform ( ) const
2022-11-01 15:11:25 -04:00
{
2023-07-18 08:42:51 -04:00
return FTransform ( FRotator ( Rotation ) , FVector ( Offset ) ) ;
}
FTransform GetSlotWorldTransform ( const FTransform & OwnerTransform ) const
{
return FTransform ( FRotator ( Rotation ) , FVector ( Offset ) ) * OwnerTransform ;
2022-11-01 15:11:25 -04:00
}
2021-09-28 13:33:00 -04:00
2022-11-01 15:11:25 -04:00
/** @return Current claim state of the slot. */
2021-11-29 11:34:31 -05:00
ESmartObjectSlotState GetState ( ) const { return State ; }
2023-11-30 02:26:33 -05:00
UE_DEPRECATED ( 5.4 , " Use CanBeClaimed() with priority instead. " )
bool CanBeClaimed ( ) const
{
return CanBeClaimed ( ESmartObjectClaimPriority : : Normal ) ;
}
/**
* Sets the slot claimed .
* @ param ClaimPriority Claim priority , a slot claimed at lower priority can be claimed by higher priority ( unless already in use ) .
* @ return True if the slot can be claimed . */
bool CanBeClaimed ( ESmartObjectClaimPriority ClaimPriority ) const
{
return IsEnabled ( )
& & ( State = = ESmartObjectSlotState : : Free
| | ( State = = ESmartObjectSlotState : : Claimed
& & ClaimedPriority < ClaimPriority ) ) ;
}
2022-09-01 09:03:19 -04:00
2022-11-01 15:11:25 -04:00
/** @return the runtime gameplay tags of the slot. */
const FGameplayTagContainer & GetTags ( ) const { return Tags ; }
2023-01-18 10:52:51 -05:00
/** @return true if both the slot and its parent smart object are enabled. */
bool IsEnabled ( ) const { return bSlotEnabled & & bObjectEnabled ; }
2022-11-01 15:11:25 -04:00
2023-02-02 18:43:13 -05:00
/** @return User data struct that can be associated to the slot when claimed or used. */
FConstStructView GetUserData ( ) const { return UserData ; }
2024-02-08 13:21:26 -05:00
FInstancedStructContainer & GetMutableStateData ( ) { return StateData ; }
const FInstancedStructContainer & GetStateData ( ) const { return StateData ; }
/** Indicates if preconditions were successfully initialized. */
bool ArePreconditionsInitialized ( ) const
{
return PreconditionState . IsInitialized ( ) ;
}
2021-09-28 13:33:00 -04:00
protected :
/** Struct could have been nested inside the subsystem but not possible with USTRUCT */
friend class USmartObjectSubsystem ;
friend struct FSmartObjectRuntime ;
2023-11-30 02:26:33 -05:00
UE_DEPRECATED ( 5.4 , " Use Claim() with priority instead. " )
bool Claim ( const FSmartObjectUserHandle & InUser )
{
return Claim ( InUser , ESmartObjectClaimPriority : : Normal ) ;
}
bool Claim ( const FSmartObjectUserHandle & InUser , ESmartObjectClaimPriority ClaimPriority ) ;
2022-11-01 15:11:25 -04:00
bool Release ( const FSmartObjectClaimHandle & ClaimHandle , const bool bAborted ) ;
2023-02-02 18:43:13 -05:00
2022-11-01 15:11:25 -04:00
friend FString LexToString ( const FSmartObjectRuntimeSlot & Slot )
2022-01-19 14:16:16 -05:00
{
2022-11-01 15:11:25 -04:00
return FString : : Printf ( TEXT ( " User:%s State:%s " ) , * LexToString ( Slot . User ) , * UEnum : : GetValueAsString ( Slot . State ) ) ;
2022-01-19 14:16:16 -05:00
}
2021-09-28 13:33:00 -04:00
2023-07-18 08:42:51 -04:00
/** Offset of the slot relative to the Smart Object. */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2023-07-18 08:42:51 -04:00
FVector3f Offset = FVector3f : : ZeroVector ;
/** Rotation of the slot relative to the Smart Object. */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2023-07-18 08:42:51 -04:00
FRotator3f Rotation = FRotator3f : : ZeroRotator ;
2022-11-01 15:11:25 -04:00
/** Runtime tags associated with this slot. */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2022-11-01 15:11:25 -04:00
FGameplayTagContainer Tags ;
2023-02-02 18:43:13 -05:00
/** Struct used to store contextual data of the user when claiming or using a slot. */
FInstancedStruct UserData ;
2021-09-28 13:33:00 -04:00
2023-07-18 08:42:51 -04:00
/** Slot state data that can be added at runtime. */
FInstancedStructContainer StateData ;
2021-09-28 13:33:00 -04:00
/** Delegate used to notify when a slot gets invalidated. See RegisterSlotInvalidationCallback */
FOnSlotInvalidated OnSlotInvalidatedDelegate ;
2022-01-19 14:16:16 -05:00
2022-11-01 15:11:25 -04:00
/** Handle to the user that reserves or uses the slot */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2022-11-01 15:11:25 -04:00
FSmartObjectUserHandle User ;
2022-11-17 07:44:24 -05:00
/** World condition runtime state. */
2022-11-30 07:17:21 -05:00
UPROPERTY ( Transient )
2022-11-17 07:44:24 -05:00
mutable FWorldConditionQueryState PreconditionState ;
2023-07-18 08:42:51 -04:00
/** Current availability state of the slot */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2023-07-18 08:42:51 -04:00
ESmartObjectSlotState State = ESmartObjectSlotState : : Free ;
2022-11-01 15:11:25 -04:00
2023-11-30 02:26:33 -05:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
ESmartObjectClaimPriority ClaimedPriority = ESmartObjectClaimPriority : : None ;
2022-11-01 15:11:25 -04:00
/** True if the slot is enabled */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2023-01-18 10:52:51 -05:00
uint8 bSlotEnabled : 1 ;
/** True if the parent smart object is enabled */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2023-01-18 10:52:51 -05:00
uint8 bObjectEnabled : 1 ;
2021-09-28 13:33:00 -04:00
} ;
2022-11-01 15:11:25 -04:00
using FSmartObjectSlotClaimState UE_DEPRECATED ( 5.2 , " Deprecated struct. Please use FSmartObjectRuntimeSlot instead. " ) = FSmartObjectRuntimeSlot ;
2021-09-28 13:33:00 -04:00
/**
2021-11-26 15:48:13 -05:00
* Struct to store and manage state of a runtime instance associated to a given smart object definition
2021-09-28 13:33:00 -04:00
*/
USTRUCT ( )
struct FSmartObjectRuntime
{
GENERATED_BODY ( )
public :
2023-07-18 08:42:51 -04:00
/* Provide default constructor to be able to compile template instantiation 'UScriptStruct::TCppStructOps<FSmartObjectRuntime>' */
/* Also public to pass void 'UScriptStruct::TCppStructOps<FSmartObjectRuntime>::ConstructForTests(void *)' */
2023-11-29 11:23:11 -05:00
FSmartObjectRuntime ( ) { }
2023-07-18 08:42:51 -04:00
2022-03-17 19:07:54 -04:00
FSmartObjectHandle GetRegisteredHandle ( ) const { return RegisteredHandle ; }
2021-09-28 13:33:00 -04:00
const FTransform & GetTransform ( ) const { return Transform ; }
2021-11-26 15:48:13 -05:00
const USmartObjectDefinition & GetDefinition ( ) const { checkf ( Definition ! = nullptr , TEXT ( " Initialized from a valid reference from the constructor " ) ) ; return * Definition ; }
2022-03-16 03:47:02 -04:00
/** Returns all tags assigned to the smart object instance */
2022-03-02 13:25:37 -05:00
const FGameplayTagContainer & GetTags ( ) const { return Tags ; }
2021-09-28 13:33:00 -04:00
2023-01-18 10:52:51 -05:00
PRAGMA_DISABLE_DEPRECATION_WARNINGS
2022-03-16 03:47:02 -04:00
/** Returns delegate that is invoked whenever a tag is added or removed */
2023-01-18 10:52:51 -05:00
UE_DEPRECATED ( 5.2 , " Tag changes are now broadcasted using FOnSmartObjectEvent. Please use GetEventDelegate(). " )
2022-03-16 03:47:02 -04:00
FOnSmartObjectTagChanged & GetTagChangedDelegate ( ) { return OnTagChangedDelegate ; }
2023-01-18 10:52:51 -05:00
PRAGMA_ENABLE_DEPRECATION_WARNINGS
2022-11-01 15:11:25 -04:00
/** @return reference to the Smart Object event delegate. */
const FOnSmartObjectEvent & GetEventDelegate ( ) const { return OnEvent ; }
/** @return mutable reference to the Smart Object event delegate. */
FOnSmartObjectEvent & GetMutableEventDelegate ( ) { return OnEvent ; }
2023-11-29 11:23:11 -05:00
/**
* Indicates if the Smart Object is enabled regardless of the reason .
* @ return True of the Smart Object is enabled .
*/
bool IsEnabled ( ) const
{
return DisableFlags = = 0 ;
}
/**
* Indicates if the Smart Object is enabled based on a specific reason .
* @ param ReasonTag Valid Tag to specify the reason for changing the enabled state of the object . Method will ensure if not valid ( i . e . None ) .
* @ return True of the Smart Object is enabled .
*/
bool IsEnabledForReason ( FGameplayTag ReasonTag ) const ;
/**
* Enables or disables the entire smart object .
* @ param ReasonTag Valid Tag to specify the reason for changing the enabled state of the object . Method will ensure if not valid ( i . e . None ) .
* @ param bEnabled Flag indicating if the object should be enable or not .
*/
void SetEnabled ( FGameplayTag ReasonTag , bool bEnabled ) ;
2022-03-16 03:47:02 -04:00
2024-02-08 13:21:26 -05:00
/**
* Returns the actor associated to the smart object instance .
* @ param TrySpawnActorIfDehydrated Indicates if the instance should try to spawn the actor / component
* associated to the smartobject if it is currently owned by an instanced actor .
* @ return Pointer to owner actor if present .
*/
AActor * GetOwnerActor ( ETrySpawnActorIfDehydrated TrySpawnActorIfDehydrated = ETrySpawnActorIfDehydrated : : No ) const ;
2023-01-18 10:52:51 -05:00
2024-02-08 13:21:26 -05:00
/**
* Returns the actor associated to the smart object instance .
* @ param TrySpawnActorIfDehydrated Indicates if the instance should try to spawn the actor / component
* associated to the smartobject if it is currently owned by an instanced actor .
* @ return Pointer to owning component if present .
*/
USmartObjectComponent * GetOwnerComponent ( ETrySpawnActorIfDehydrated TrySpawnActorIfDehydrated = ETrySpawnActorIfDehydrated : : No ) const ;
2024-01-30 10:11:23 -05:00
2022-11-01 15:11:25 -04:00
/** @return handle of the specified slot. */
2023-07-18 08:42:51 -04:00
const FSmartObjectRuntimeSlot & GetSlot ( const int32 Index ) const
{
return Slots [ Index ] ;
}
FSmartObjectRuntimeSlot & GetMutableSlot ( const int32 Index )
{
return Slots [ Index ] ;
}
TConstArrayView < FSmartObjectRuntimeSlot > GetSlots ( ) const
{
return Slots ;
}
UE_DEPRECATED ( 5.3 , " You can access the slots directly via GetSlots(). " )
2022-11-01 15:11:25 -04:00
FSmartObjectSlotHandle GetSlotHandle ( const int32 Index ) const
{
2023-07-18 08:42:51 -04:00
return { } ;
2022-11-01 15:11:25 -04:00
}
2023-07-18 08:42:51 -04:00
2024-02-08 13:21:26 -05:00
/** Indicates if preconditions were successfully initialized. */
bool ArePreconditionsInitialized ( ) const
{
return PreconditionState . IsInitialized ( ) ;
}
2023-11-29 11:23:11 -05:00
# if WITH_SMARTOBJECT_DEBUG
FString DebugGetDisableFlagsString ( ) const ;
# endif // WITH_SMARTOBJECT_DEBUG
2021-09-28 13:33:00 -04:00
private :
/** Struct could have been nested inside the subsystem but not possible with USTRUCT */
friend class USmartObjectSubsystem ;
2021-11-26 15:48:13 -05:00
explicit FSmartObjectRuntime ( const USmartObjectDefinition & Definition ) ;
2021-09-28 13:33:00 -04:00
void SetTransform ( const FTransform & Value ) { Transform = Value ; }
2022-03-02 13:25:37 -05:00
void SetRegisteredHandle ( const FSmartObjectHandle Value ) { RegisteredHandle = Value ; }
2021-09-28 13:33:00 -04:00
2023-11-29 11:23:11 -05:00
/**
* Enables or disables the entire smart object using the bit mask from a reason tag .
* @ param bEnabled Flag indicating if the object should be enable or not .
* @ param ReasonMask Bit mask associated to the reason for disabling the object .
*/
void SetEnabled ( bool bEnabled , uint16 ReasonMask ) ;
2024-02-08 13:21:26 -05:00
/**
* Creates full actor from instanced actor owner , if any .
* That actor will register its SmartObjectComponents that will then update OwnerComponent .
*/
bool ResolveOwnerActor ( ) const ;
2023-01-18 10:52:51 -05:00
/** World condition runtime state. */
UPROPERTY ( Transient )
mutable FWorldConditionQueryState PreconditionState ;
2023-07-18 08:42:51 -04:00
/** Runtime slots */
UPROPERTY ( Transient )
TArray < FSmartObjectRuntimeSlot > Slots ;
2021-09-28 13:33:00 -04:00
2021-11-26 15:48:13 -05:00
/** Associated smart object definition */
UPROPERTY ( )
2022-08-18 15:08:49 -04:00
TObjectPtr < const USmartObjectDefinition > Definition = nullptr ;
2021-09-28 13:33:00 -04:00
2023-01-18 10:52:51 -05:00
/** Component that owns the Smart Object. May be empty if the parent Actor is not loaded. */
2022-11-23 09:11:13 -05:00
UPROPERTY ( )
2023-01-18 10:52:51 -05:00
TWeakObjectPtr < USmartObjectComponent > OwnerComponent ;
2024-02-08 13:21:26 -05:00
/** Struct used to store contextual data of the owner of that SmartObject. */
FInstancedStruct OwnerData ;
2022-11-23 09:11:13 -05:00
2021-09-28 13:33:00 -04:00
/** Instance specific transform */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2021-09-28 13:33:00 -04:00
FTransform Transform ;
/** Tags applied to the current instance */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2021-09-28 13:33:00 -04:00
FGameplayTagContainer Tags ;
2022-03-16 03:47:02 -04:00
/** Delegate fired whenever a new tag is added or an existing one gets removed */
2023-01-18 10:52:51 -05:00
PRAGMA_DISABLE_DEPRECATION_WARNINGS
2022-03-16 03:47:02 -04:00
FOnSmartObjectTagChanged OnTagChangedDelegate ;
2023-01-18 10:52:51 -05:00
PRAGMA_ENABLE_DEPRECATION_WARNINGS
2022-03-16 03:47:02 -04:00
2023-01-18 10:52:51 -05:00
/** Delegate that is fired when the Smart Object changes. */
2022-11-01 15:11:25 -04:00
FOnSmartObjectEvent OnEvent ;
2022-01-19 14:16:16 -05:00
/** RegisteredHandle != FSmartObjectHandle::Invalid when registered with SmartObjectSubsystem */
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2022-01-19 14:16:16 -05:00
FSmartObjectHandle RegisteredHandle ;
2021-09-28 13:33:00 -04:00
2022-02-21 01:10:34 -05:00
/** Spatial representation data associated to the current instance */
2022-05-22 10:30:02 -04:00
UPROPERTY ( EditDefaultsOnly , Category = " SmartObject " , meta = ( BaseStruct = " /Script/SmartObjectsModule.SmartObjectSpatialEntryData " , ExcludeBaseStruct ) )
2022-02-21 01:10:34 -05:00
FInstancedStruct SpatialEntryData ;
# if UE_ENABLE_DEBUG_DRAWING
FBox Bounds = FBox ( EForceInit : : ForceInit ) ;
# endif
2022-03-16 03:47:02 -04:00
2023-11-29 11:23:11 -05:00
/**
* Each slot has its own enabled state but the parent instance also have a more high level state that could be split into different reasons .
* Note : The enabled state is stored as disable bits to make it easier to check for " is the object disabled for a given or any reason " .
*/
2023-08-22 12:17:21 -04:00
UPROPERTY ( Transient , VisibleAnywhere , Category = SmartObjects )
2023-11-29 11:23:11 -05:00
uint16 DisableFlags = 0 ;
public :
static constexpr int32 MaxNumDisableFlags = sizeof ( DisableFlags ) * 8 ;
2021-09-28 13:33:00 -04:00
} ;
2022-01-19 14:16:16 -05:00
USTRUCT ( )
struct SMARTOBJECTSMODULE_API FSmartObjectSlotView
{
GENERATED_BODY ( )
public :
FSmartObjectSlotView ( ) = default ;
2023-07-18 08:42:51 -04:00
bool IsValid ( ) const { return SlotHandle . IsValid ( ) & & Runtime & & Slot ; }
2022-03-16 03:47:02 -04:00
2023-07-18 08:42:51 -04:00
FSmartObjectSlotHandle GetSlotHandle ( ) const { return SlotHandle ; }
2022-01-19 14:16:16 -05:00
/**
* Returns a reference to the slot state data of the specified type .
* Method will fail a check if the slot doesn ' t have the given type .
*/
template < typename T >
T & GetStateData ( ) const
{
static_assert ( TIsDerivedFrom < T , FSmartObjectSlotStateData > : : IsDerived ,
" Given struct doesn't represent a valid runtime data type. Make sure to inherit from FSmartObjectSlotStateData or one of its child-types. " ) ;
2023-07-18 08:42:51 -04:00
checkf ( Slot , TEXT ( " StateData can only be accessed through a valid SlotView " ) ) ;
T * Item = nullptr ;
for ( FStructView Data : Slot - > GetMutableStateData ( ) )
{
Item = Data . template GetPtr < T > ( ) ;
if ( Item ! = nullptr )
{
break ;
}
}
check ( Item ) ;
return * Item ;
2022-01-19 14:16:16 -05:00
}
/**
* Returns a pointer to the slot state data of the specified type .
* Method will return null if the slot doesn ' t have the given type .
*/
template < typename T >
T * GetStateDataPtr ( ) const
{
static_assert ( TIsDerivedFrom < T , FSmartObjectSlotStateData > : : IsDerived ,
" Given struct doesn't represent a valid runtime data type. Make sure to inherit from FSmartObjectSlotStateData or one of its child-types. " ) ;
2023-07-18 08:42:51 -04:00
checkf ( Slot , TEXT ( " StateData can only be accessed through a valid SlotView " ) ) ;
for ( FStructView Data : Slot - > GetMutableStateData ( ) )
{
if ( T * Item = Data . template GetPtr < T > ( ) )
{
return Item ;
}
}
return nullptr ;
2022-01-19 14:16:16 -05:00
}
2022-02-17 03:40:43 -05:00
/**
* Returns a reference to the definition of the slot ' s parent object .
* Method will fail a check if called on an invalid SlotView .
* @ note The definition fragment is always created and assigned when creating an entity associated to a slot
* so a valid SlotView is guaranteed to be able to provide it .
*/
const USmartObjectDefinition & GetSmartObjectDefinition ( ) const
{
2023-07-18 08:42:51 -04:00
checkf ( Runtime , TEXT ( " Definition can only be accessed through a valid SlotView " ) ) ;
return Runtime - > GetDefinition ( ) ;
2022-02-17 03:40:43 -05:00
}
2022-01-19 14:16:16 -05:00
/**
* Returns a reference to the main definition of the slot .
* Method will fail a check if called on an invalid SlotView .
*/
const FSmartObjectSlotDefinition & GetDefinition ( ) const
{
2023-07-18 08:42:51 -04:00
checkf ( Runtime , TEXT ( " Definition can only be accessed through a valid SlotView " ) ) ;
return Runtime - > GetDefinition ( ) . GetSlot ( SlotHandle . GetSlotIndex ( ) ) ;
2022-01-19 14:16:16 -05:00
}
2022-03-02 22:33:53 -05:00
/**
* Fills the provided GameplayTagContainer with the activity tags associated to the slot according to the tag filtering policy .
* Method will fail a check if called on an invalid SlotView .
*/
void GetActivityTags ( FGameplayTagContainer & OutActivityTags ) const
{
2023-07-18 08:42:51 -04:00
GetSmartObjectDefinition ( ) . GetSlotActivityTags ( GetDefinition ( ) , OutActivityTags ) ;
2022-03-02 22:33:53 -05:00
}
2022-01-19 14:16:16 -05:00
/**
* Returns a reference to the definition data of the specified type from the main slot definition .
* Method will fail a check if the slot definition doesn ' t contain the given type .
*/
template < typename T >
const T & GetDefinitionData ( ) const
{
const FSmartObjectSlotDefinition & SlotDefinition = GetDefinition ( ) ;
2023-12-04 07:36:52 -05:00
return SlotDefinition . template GetDefinitionData < T > ( ) ;
2022-01-19 14:16:16 -05:00
}
/**
* Returns a pointer to the definition data of the specified type from the main slot definition .
* Method will return null if the slot doesn ' t contain the given type .
*/
template < typename T >
const T * GetDefinitionDataPtr ( ) const
{
const FSmartObjectSlotDefinition & SlotDefinition = GetDefinition ( ) ;
2023-12-04 07:36:52 -05:00
return SlotDefinition . template GetDefinitionDataPtr < T > ( ) ;
2022-01-19 14:16:16 -05:00
}
2022-11-01 15:11:25 -04:00
/** @return the claim state of the slot. */
ESmartObjectSlotState GetState ( ) const
{
checkf ( Slot , TEXT ( " State can only be accessed through a valid SlotView " ) ) ;
return Slot - > GetState ( ) ;
}
2023-11-30 02:26:33 -05:00
UE_DEPRECATED ( 5.4 , " Use CanBeClaimed() with priority instead. " )
2022-11-01 15:11:25 -04:00
bool CanBeClaimed ( ) const
{
2023-11-30 02:26:33 -05:00
return CanBeClaimed ( ESmartObjectClaimPriority : : Normal ) ;
2022-11-01 15:11:25 -04:00
}
2023-11-30 02:26:33 -05:00
/** @return true of the slot can be claimed. */
bool CanBeClaimed ( ESmartObjectClaimPriority ClaimPriority ) const
{
checkf ( Slot , TEXT ( " Claim can only be accessed through a valid SlotView " ) ) ;
return Slot - > CanBeClaimed ( ClaimPriority ) ;
}
/** @return true if the slot and the object is enabled. */
bool IsEnabled ( ) const
{
checkf ( Slot , TEXT ( " Enabled can only be accessed through a valid SlotView " ) ) ;
return Slot - > IsEnabled ( ) ;
}
2022-11-01 15:11:25 -04:00
/** @return runtime gameplay tags of the slot. */
const FGameplayTagContainer & GetTags ( ) const
{
checkf ( Slot , TEXT ( " Tags can only be accessed through a valid SlotView " ) ) ;
return Slot - > GetTags ( ) ;
}
/** @return handle to the owning Smart Object. */
FSmartObjectHandle GetOwnerRuntimeObject ( ) const
{
2023-07-18 08:42:51 -04:00
return SlotHandle . GetSmartObjectHandle ( ) ;
2022-11-01 15:11:25 -04:00
}
2022-01-19 14:16:16 -05:00
private :
friend class USmartObjectSubsystem ;
2023-07-18 08:42:51 -04:00
FSmartObjectSlotView ( const FSmartObjectSlotHandle InSlotHandle , FSmartObjectRuntime & InRuntime , FSmartObjectRuntimeSlot & InSlot )
: SlotHandle ( InSlotHandle )
, Runtime ( & InRuntime )
, Slot ( & InSlot )
2022-08-12 07:56:27 -04:00
{ }
2022-01-19 14:16:16 -05:00
2023-07-18 08:42:51 -04:00
FSmartObjectSlotHandle SlotHandle ;
FSmartObjectRuntime * Runtime ;
FSmartObjectRuntimeSlot * Slot ;
2022-01-19 14:16:16 -05:00
} ;