Files
UnrealEngine/Engine/Plugins/Media/ElectraUtil/Source/ElectraBase/Public/ParameterDictionary.h
Brandyn / Techy fcc1b09210 init
2026-04-04 15:40:51 -05:00

295 lines
8.2 KiB
C++

// Copyright Epic Games, Inc. All Rights Reserved.
#pragma once
#include "CoreMinimal.h"
#include "Misc/ScopeLock.h"
#include "PlayerTime.h"
#include "Templates/TypeCompatibleBytes.h"
#include "Containers/Array.h"
#include "Misc/Variant.h"
#include "Misc/Timespan.h"
#include "Misc/Timecode.h"
#include "Misc/FrameRate.h"
#define UE_API ELECTRABASE_API
namespace Electra
{
class FVariantValue
{
class FSharedPtrHolderBase
{
public:
virtual ~FSharedPtrHolderBase() {}
virtual void SetValueOn(FSharedPtrHolderBase* Dst) const = 0;
};
template<typename T> class TSharedPtrHolder : public FSharedPtrHolderBase
{
using SharedPtrType = TSharedPtr<T, ESPMode::ThreadSafe>;
public:
TSharedPtrHolder(const SharedPtrType & InPointer)
: Pointer(InPointer)
{}
SharedPtrType Pointer;
virtual void SetValueOn(FSharedPtrHolderBase* Dst) const override
{
new(Dst) TSharedPtrHolder<T>(reinterpret_cast<const SharedPtrType&>(Pointer));
}
};
public:
UE_API FVariantValue();
UE_API ~FVariantValue();
UE_API FVariantValue(const FVariantValue& rhs);
UE_API FVariantValue& operator=(const FVariantValue& rhs);
UE_API explicit FVariantValue(const FString& StringValue);
UE_API explicit FVariantValue(double DoubleValue);
UE_API explicit FVariantValue(int64 Int64Value);
UE_API explicit FVariantValue(bool BoolValue);
UE_API explicit FVariantValue(const FTimeValue& TimeValue);
UE_API explicit FVariantValue(const FTimespan& TimespanValue);
UE_API explicit FVariantValue(const FTimecode& TimecodeValue);
UE_API explicit FVariantValue(const FFrameRate& FramerateValue);
UE_API explicit FVariantValue(void* PointerValue);
template<typename T> explicit FVariantValue(const TSharedPtr<T, ESPMode::ThreadSafe>& PointerValue)
: DataType(EDataType::TypeUninitialized)
{
Set(PointerValue);
}
UE_API explicit FVariantValue(const TArray<uint8>& ArrayValue);
UE_API FVariantValue& Set(const FString& StringValue);
UE_API FVariantValue& Set(double DoubleValue);
UE_API FVariantValue& Set(int64 Int64Value);
UE_API FVariantValue& Set(bool BoolValue);
UE_API FVariantValue& Set(const FTimeValue& TimeValue);
UE_API FVariantValue& Set(const FTimespan& TimespanValue);
UE_API FVariantValue& Set(const FTimecode& TimecodeValue);
UE_API FVariantValue& Set(const FFrameRate& FramerateValue);
UE_API FVariantValue& Set(void* PointerValue);
template <typename T> FVariantValue& Set(const TSharedPtr<T, ESPMode::ThreadSafe>& PointerValue)
{
Clear();
new(&DataBuffer) TSharedPtrHolder<T>(PointerValue);
DataType = EDataType::TypeSharedPointer;
return *this;
}
UE_API FVariantValue& Set(const TArray<uint8>& ArrayValue);
// Returns variant value. Type *must* match. Otherwise an empty/zero value is returned.
UE_API const FString& GetFString() const;
UE_API const double& GetDouble() const;
UE_API const int64& GetInt64() const;
UE_API const bool& GetBool() const;
UE_API const FTimeValue& GetTimeValue() const;
UE_API const FTimespan& GetTimespan() const;
UE_API const FTimecode& GetTimecode() const;
UE_API const FFrameRate& GetFramerate() const;
UE_API void* const & GetPointer() const;
template<typename T> TSharedPtr<T, ESPMode::ThreadSafe> GetSharedPointer() const
{
if (ensure(DataType == EDataType::TypeSharedPointer))
{
const TSharedPtrHolder<T>* Pointer = reinterpret_cast<const TSharedPtrHolder<T>*>(&DataBuffer);
return Pointer->Pointer;
}
else
{
return TSharedPtr<T, ESPMode::ThreadSafe>();
}
}
UE_API const TArray<uint8>& GetArray() const;
// Returns variant value. If type does not match the specified default will be returned.
UE_API const FString& SafeGetFString(const FString& Default = FString()) const;
UE_API double SafeGetDouble(double Default=0.0) const;
UE_API int64 SafeGetInt64(int64 Default=0) const;
UE_API bool SafeGetBool(bool Default=false) const;
UE_API FTimeValue SafeGetTimeValue(const FTimeValue& Default=FTimeValue()) const;
UE_API FTimespan SafeGetTimespan(const FTimespan& Default=FTimespan()) const;
UE_API FTimecode SafeGetTimecode(const FTimecode& Default=FTimecode()) const;
UE_API FFrameRate SafeGetFramerate(const FFrameRate& Default=FFrameRate()) const;
UE_API void* SafeGetPointer(void* Default=nullptr) const;
UE_API const TArray<uint8>& SafeGetArray() const;
enum class EDataType
{
TypeUninitialized,
TypeFString,
TypeDouble,
TypeInt64,
TypeBoolean,
TypeTimeValue,
TypeTimespanValue,
TypeTimecodeValue,
TypeFramerateValue,
TypeVoidPointer,
TypeSharedPointer,
TypeU8Array,
};
EDataType GetDataType() const
{
return DataType;
}
bool IsValid() const
{
return DataType != EDataType::TypeUninitialized;
}
bool IsType(EDataType type) const
{
return DataType == type;
}
UE_API FVariant ToFVariant() const;
private:
union FUnionLayout
{
uint8 MemSizeFString[sizeof(FString)];
uint8 MemSizeDouble[sizeof(double)];
uint8 MemSizeInt64[sizeof(int64)];
uint8 MemSizeVoidPtr[sizeof(void*)];
uint8 MemSizeBoolean[sizeof(bool)];
uint8 MemSizeTimeValue[sizeof(FTimeValue)];
uint8 MemSizeTimespan[sizeof(FTimespan)];
uint8 MemSizeTimecode[sizeof(FTimecode)];
uint8 MemSizeFramerate[sizeof(FFrameRate)];
uint8 MemSizeSharedPtrValue[sizeof(TSharedPtrHolder<uint8>)];
uint8 MemSizeTArray[sizeof(TArray<uint8>)];
};
UE_API void Clear();
UE_API void CopyInternal(const FVariantValue& FromOther);
TAlignedBytes<sizeof(FUnionLayout), 16> DataBuffer;
EDataType DataType;
};
class FParamDict
{
public:
FParamDict() {}
UE_API FParamDict(const FParamDict& Other);
UE_API FParamDict& operator=(const FParamDict& Other);
~FParamDict() = default;
UE_API void Clear();
UE_API void Set(const FName& Key, const FVariantValue& Value);
UE_API void Set(const FName& Key, FVariantValue&& Value);
UE_API void GetKeys(TArray<FName>& OutKeys) const;
UE_API bool HaveKey(const FName& Key) const;
UE_API FVariantValue GetValue(const FName& Key) const;
UE_API void Remove(const FName& Key);
UE_API bool SetValueFrom(FName InKey, const FParamDict& InOther);
UE_API void ConvertTo(TMap<FString, FVariant>& OutVariantMap, const FString& InAddPrefixToKey) const;
UE_API void ConvertKeysStartingWithTo(TMap<FString, FVariant>& OutVariantMap, const FString& InKeyStartsWith, const FString& InAddPrefixToKey) const;
private:
UE_API void InternalCopy(const FParamDict& Other);
TMap<FName, FVariantValue> Dictionary;
};
class FParamDictTS
{
public:
FParamDictTS() {}
FParamDictTS(const FParamDictTS& Other)
{
Dictionary = Other.Dictionary;
}
FParamDictTS& operator=(const FParamDictTS& Other)
{
if (&Other != this)
{
FScopeLock lock(&Lock);
Dictionary = Other.Dictionary;
}
return *this;
}
FParamDictTS& operator=(const FParamDict& Other)
{
FScopeLock lock(&Lock);
Dictionary = Other;
return *this;
}
~FParamDictTS() = default;
FParamDict GetDictionary() const
{
FScopeLock lock(&Lock);
return Dictionary;
}
void Clear()
{
FScopeLock lock(&Lock);
Dictionary.Clear();
}
void Set(const FName& Key, const FVariantValue& Value)
{
FScopeLock lock(&Lock);
Dictionary.Set(Key, Value);
}
void Set(const FName& Key, FVariantValue&& Value)
{
FScopeLock lock(&Lock);
Dictionary.Set(Key, MoveTemp(Value));
}
void GetKeys(TArray<FName>& OutKeys) const
{
FScopeLock lock(&Lock);
Dictionary.GetKeys(OutKeys);
}
bool HaveKey(const FName& Key) const
{
FScopeLock lock(&Lock);
return Dictionary.HaveKey(Key);
}
FVariantValue GetValue(const FName& Key) const
{
FScopeLock lock(&Lock);
return Dictionary.GetValue(Key);
}
void Remove(const FName& Key)
{
FScopeLock lock(&Lock);
Dictionary.Remove(Key);
}
bool SetValueFrom(FName InKey, const FParamDict& InOther)
{
FScopeLock lock(&Lock);
return Dictionary.SetValueFrom(InKey, InOther);
}
void ConvertTo(TMap<FString, FVariant>& OutVariantMap, const FString& InAddPrefixToKey) const
{
FScopeLock lock(&Lock);
Dictionary.ConvertTo(OutVariantMap, InAddPrefixToKey);
}
void ConvertKeysStartingWithTo(TMap<FString, FVariant>& OutVariantMap, const FString& InKeyStartsWith, const FString& InAddPrefixToKey) const
{
FScopeLock lock(&Lock);
Dictionary.ConvertKeysStartingWithTo(OutVariantMap, InKeyStartsWith, InAddPrefixToKey);
}
private:
mutable FCriticalSection Lock;
FParamDict Dictionary;
};
} // namespace Electra
#undef UE_API