Files
UnrealEngineUWP/Engine/Plugins/Runtime/Metasound/Source/MetasoundFrontend/Private/MetasoundFrontendRegistries.cpp
helen yang fa585989cf Fix ensures when migrating MetaSound assets
- Create new class names for temporary packages created during migration to avoid duplicate node registration
- Change duplicate node registration ensure to if check with better logging of asset causing collision

#jira UE-161039
#jira UE-175059
#jira UE-188854
#rb rob.gay

[CL 26299244 by helen yang in ue5-main branch]
2023-06-28 17:08:29 -04:00

753 lines
24 KiB
C++

// Copyright Epic Games, Inc. All Rights Reserved.
#include "MetasoundFrontendRegistries.h"
#include "Algo/ForEach.h"
#include "CoreMinimal.h"
#include "HAL/PlatformTime.h"
#include "MetasoundFrontendDataTypeRegistry.h"
#include "MetasoundFrontendNodeRegistryPrivate.h"
#include "MetasoundFrontendRegistryTransaction.h"
#include "MetasoundFrontendSearchEngine.h"
#include "MetasoundLog.h"
#include "MetasoundRouter.h"
#include "MetasoundTrace.h"
#include "Misc/ScopeLock.h"
namespace Metasound
{
namespace Frontend
{
namespace MetasoundFrontendRegistryPrivate
{
const FString& GetClassTypeString(EMetasoundFrontendClassType InType)
{
static const FString InputType(TEXT("Input"));
static const FString OutputType(TEXT("Output"));
static const FString ExternalType(TEXT("External"));
static const FString VariableAccessorType(TEXT("VariableAccessor"));
static const FString VariableDeferredAccessorType(TEXT("VariableDeferredAccessor"));
static const FString VariableMutatorType(TEXT("VariableMutator"));
static const FString VariableType(TEXT("Variable"));
static const FString LiteralType(TEXT("Literal"));
static const FString GraphType(TEXT("Graph"));
static const FString TemplateType(TEXT("Template"));
static const FString InvalidType(TEXT("Invalid"));
switch (InType)
{
case EMetasoundFrontendClassType::Input:
return InputType;
case EMetasoundFrontendClassType::Output:
return OutputType;
case EMetasoundFrontendClassType::External:
return ExternalType;
case EMetasoundFrontendClassType::Literal:
return LiteralType;
case EMetasoundFrontendClassType::Variable:
return VariableType;
case EMetasoundFrontendClassType::VariableDeferredAccessor:
return VariableDeferredAccessorType;
case EMetasoundFrontendClassType::VariableAccessor:
return VariableAccessorType;
case EMetasoundFrontendClassType::VariableMutator:
return VariableMutatorType;
case EMetasoundFrontendClassType::Template:
return TemplateType;
case EMetasoundFrontendClassType::Graph:
return GraphType;
default:
static_assert(static_cast<uint8>(EMetasoundFrontendClassType::Invalid) == 10, "Missing EMetasoundFrontendClassType case coverage");
return InvalidType;
}
}
}
FRegistryContainerImpl* FRegistryContainerImpl::LazySingleton = nullptr;
FRegistryContainerImpl& FRegistryContainerImpl::Get()
{
if (!LazySingleton)
{
LazySingleton = new Metasound::Frontend::FRegistryContainerImpl();
}
return *LazySingleton;
}
void FRegistryContainerImpl::Shutdown()
{
if (nullptr != LazySingleton)
{
delete LazySingleton;
LazySingleton = nullptr;
}
}
FRegistryContainerImpl::FRegistryContainerImpl()
: TransactionBuffer(MakeShared<FNodeRegistryTransactionBuffer>())
{
}
void FRegistryContainerImpl::RegisterPendingNodes()
{
METASOUND_LLM_SCOPE;
METASOUND_TRACE_CPUPROFILER_EVENT_SCOPE(metasound::FRegistryContainerImpl::RegisterPendingNodes);
{
FScopeLock ScopeLock(&LazyInitCommandCritSection);
for (TUniqueFunction<void()>& Command : LazyInitCommands)
{
Command();
}
LazyInitCommands.Empty();
}
// Prime search engine after bulk registration.
ISearchEngine::Get().Prime();
}
bool FRegistryContainerImpl::EnqueueInitCommand(TUniqueFunction<void()>&& InFunc)
{
FScopeLock ScopeLock(&LazyInitCommandCritSection);
if (LazyInitCommands.Num() >= MaxNumNodesAndDatatypesToInitialize)
{
UE_LOG(LogMetaSound, Warning, TEXT("Registering more that %d nodes and datatypes for metasounds! Consider increasing MetasoundFrontendRegistryContainer::MaxNumNodesAndDatatypesToInitialize."), MaxNumNodesAndDatatypesToInitialize);
}
LazyInitCommands.Add(MoveTemp(InFunc));
return true;
}
void FRegistryContainerImpl::ForEachNodeRegistryTransactionSince(FRegistryTransactionID InSince, FRegistryTransactionID* OutCurrentRegistryTransactionID, TFunctionRef<void(const FNodeRegistryTransaction&)> InFunc) const
{
UE_LOG(LogMetaSound, Error, TEXT("FMetasoundFrontendRegistryContainer::ForEachNodeRegistryTransactionSince is no longer supported and will not function as expected."));
}
TUniquePtr<Metasound::INode> FRegistryContainerImpl::CreateNode(const FNodeRegistryKey& InKey, const Metasound::FNodeInitData& InInitData) const
{
if (const INodeRegistryEntry* Entry = FindNodeEntry(InKey))
{
return Entry->CreateNode(InInitData);
}
// Because creation of external nodes can rely on assets being unavailable due to errors in loading order, asset(s)
// missing, etc. only log error and don't throw ensure to avoid blocking start-up if assets are missing. All other
// CreateNode calls are natively managed and thus better suited to throw ensures.
UE_LOG(LogMetaSound, Error, TEXT("Could not find node [RegistryKey:%s]"), *InKey);
return nullptr;
}
TUniquePtr<Metasound::INode> FRegistryContainerImpl::CreateNode(const FNodeRegistryKey& InKey, FDefaultLiteralNodeConstructorParams&& InParams) const
{
const INodeRegistryEntry* Entry = FindNodeEntry(InKey);
if (ensureAlwaysMsgf(nullptr != Entry, TEXT("Could not find node [RegistryKey:%s]"), *InKey))
{
return Entry->CreateNode(MoveTemp(InParams));
}
return nullptr;
}
TUniquePtr<Metasound::INode> FRegistryContainerImpl::CreateNode(const FNodeRegistryKey& InKey, FDefaultNamedVertexNodeConstructorParams&& InParams) const
{
const INodeRegistryEntry* Entry = FindNodeEntry(InKey);
if (ensureAlwaysMsgf(nullptr != Entry, TEXT("Could not find node [RegistryKey:%s]"), *InKey))
{
return Entry->CreateNode(MoveTemp(InParams));
}
return nullptr;
}
TUniquePtr<Metasound::INode> FRegistryContainerImpl::CreateNode(const FNodeRegistryKey& InKey, FDefaultNamedVertexWithLiteralNodeConstructorParams&& InParams) const
{
const INodeRegistryEntry* Entry = FindNodeEntry(InKey);
if (ensureAlwaysMsgf(nullptr != Entry, TEXT("Could not find node [RegistryKey:%s]"), *InKey))
{
return Entry->CreateNode(MoveTemp(InParams));
}
return nullptr;
}
TArray<::Metasound::Frontend::FConverterNodeInfo> FRegistryContainerImpl::GetPossibleConverterNodes(const FName& FromDataType, const FName& ToDataType)
{
FConverterNodeRegistryKey InKey = { FromDataType, ToDataType };
if (!ConverterNodeRegistry.Contains(InKey))
{
return TArray<FConverterNodeInfo>();
}
else
{
return ConverterNodeRegistry[InKey].PotentialConverterNodes;
}
}
TUniquePtr<FNodeRegistryTransactionStream> FRegistryContainerImpl::CreateTransactionStream()
{
return MakeUnique<FNodeRegistryTransactionStream>(TransactionBuffer);
}
FNodeRegistryKey FRegistryContainerImpl::RegisterNode(TUniquePtr<INodeRegistryEntry>&& InEntry)
{
METASOUND_LLM_SCOPE;
FNodeRegistryKey Key;
if (InEntry.IsValid())
{
TSharedRef<INodeRegistryEntry, ESPMode::ThreadSafe> Entry(InEntry.Release());
FNodeRegistryTransaction::FTimeType Timestamp = FPlatformTime::Cycles64();
Key = NodeRegistryKey::CreateKey(Entry->GetClassInfo());
// check to see if an identical node was already registered, and log
if (RegisteredNodes.Contains(Key))
{
TSharedRef<INodeRegistryEntry, ESPMode::ThreadSafe> Node = RegisteredNodes[Key];
const FNodeClassInfo& ClassInfo = Node->GetClassInfo();
UE_LOG(LogMetaSound, Error, TEXT("Node with registry key '%s' already registered by asset '%s'. The previously registered node will be overwritten. "
"This can happen if two classes share the same name or if METASOUND_REGISTER_NODE is defined in a public header."
), *Key, *ClassInfo.AssetPath.ToString());
}
// Store update to newly registered node in history so nodes
// can be queried by transaction ID
TransactionBuffer->AddTransaction(FNodeRegistryTransaction(FNodeRegistryTransaction::ETransactionType::NodeRegistration, Entry->GetClassInfo(), Timestamp));
// Store registry elements in map so nodes can be queried using registry key.
RegisteredNodes.Add(Key, Entry);
}
return Key;
}
FNodeRegistryKey FRegistryContainerImpl::RegisterNodeTemplate(TUniquePtr<INodeRegistryTemplateEntry>&& InEntry)
{
METASOUND_LLM_SCOPE;
FNodeRegistryKey Key;
if (InEntry.IsValid())
{
TSharedRef<INodeRegistryTemplateEntry, ESPMode::ThreadSafe> Entry(InEntry.Release());
FNodeRegistryTransaction::FTimeType Timestamp = FPlatformTime::Cycles64();
Key = NodeRegistryKey::CreateKey(Entry->GetClassInfo());
// check to see if an identical node was already registered, and log
ensureAlwaysMsgf(
!RegisteredNodes.Contains(Key),
TEXT("Node template with registry key '%s' already registered. The previously registered node will be overwritten."),
*Key);
// Store update to newly registered node in history so nodes
// can be queried by transaction ID
TransactionBuffer->AddTransaction(FNodeRegistryTransaction(FNodeRegistryTransaction::ETransactionType::NodeRegistration, Entry->GetClassInfo(), Timestamp));
// Store registry elements in map so nodes can be queried using registry key.
RegisteredNodeTemplates.Add(Key, Entry);
}
return Key;
}
bool FRegistryContainerImpl::UnregisterNode(const FNodeRegistryKey& InKey)
{
METASOUND_LLM_SCOPE;
if (NodeRegistryKey::IsValid(InKey))
{
if (const INodeRegistryEntry* Entry = FindNodeEntry(InKey))
{
FNodeRegistryTransaction::FTimeType Timestamp = FPlatformTime::Cycles64();
TransactionBuffer->AddTransaction(FNodeRegistryTransaction(FNodeRegistryTransaction::ETransactionType::NodeUnregistration, Entry->GetClassInfo(), Timestamp));
RegisteredNodes.Remove(InKey);
return true;
}
}
return false;
}
bool FRegistryContainerImpl::UnregisterNodeTemplate(const FNodeRegistryKey& InKey)
{
METASOUND_LLM_SCOPE;
if (NodeRegistryKey::IsValid(InKey))
{
if (const INodeRegistryTemplateEntry* Entry = FindNodeTemplateEntry(InKey))
{
FNodeRegistryTransaction::FTimeType Timestamp = FPlatformTime::Cycles64();
TransactionBuffer->AddTransaction(FNodeRegistryTransaction(FNodeRegistryTransaction::ETransactionType::NodeUnregistration, Entry->GetClassInfo(), Timestamp));
RegisteredNodeTemplates.Remove(InKey);
return true;
}
}
return false;
}
bool FRegistryContainerImpl::RegisterConversionNode(const FConverterNodeRegistryKey& InNodeKey, const FConverterNodeInfo& InNodeInfo)
{
if (!ConverterNodeRegistry.Contains(InNodeKey))
{
ConverterNodeRegistry.Add(InNodeKey);
}
FConverterNodeRegistryValue& ConverterNodeList = ConverterNodeRegistry[InNodeKey];
if (ensureAlways(!ConverterNodeList.PotentialConverterNodes.Contains(InNodeInfo)))
{
ConverterNodeList.PotentialConverterNodes.Add(InNodeInfo);
return true;
}
else
{
// If we hit this, someone attempted to add the same converter node to our list multiple times.
return false;
}
}
bool FRegistryContainerImpl::IsNodeRegistered(const FNodeRegistryKey& InKey) const
{
return RegisteredNodes.Contains(InKey) || RegisteredNodeTemplates.Contains(InKey);
}
bool FRegistryContainerImpl::IsNodeNative(const FNodeRegistryKey& InKey) const
{
if (const INodeRegistryEntry* Entry = FindNodeEntry(InKey))
{
return Entry->IsNative();
}
if (const INodeRegistryTemplateEntry* TemplateEntry = FindNodeTemplateEntry(InKey))
{
return true;
}
return false;
}
bool FRegistryContainerImpl::FindFrontendClassFromRegistered(const FNodeRegistryKey& InKey, FMetasoundFrontendClass& OutClass)
{
if (const INodeRegistryEntry* Entry = FindNodeEntry(InKey))
{
OutClass = Entry->GetFrontendClass();
return true;
}
if (const INodeRegistryTemplateEntry* Entry = FindNodeTemplateEntry(InKey))
{
OutClass = Entry->GetFrontendClass();
return true;
}
return false;
}
const TSet<FMetasoundFrontendVersion>* FRegistryContainerImpl::FindImplementedInterfacesFromRegistered(const Metasound::Frontend::FNodeRegistryKey& InKey) const
{
if (const INodeRegistryEntry* Entry = FindNodeEntry(InKey))
{
return Entry->GetImplementedInterfaces();
}
return nullptr;
}
bool FRegistryContainerImpl::FindNodeClassInfoFromRegistered(const Metasound::Frontend::FNodeRegistryKey& InKey, FNodeClassInfo& OutInfo)
{
if (const INodeRegistryEntry* Entry = FindNodeEntry(InKey))
{
OutInfo = Entry->GetClassInfo();
return true;
}
if (const INodeRegistryTemplateEntry* Entry = FindNodeTemplateEntry(InKey))
{
OutInfo = Entry->GetClassInfo();
return true;
}
return false;
}
bool FRegistryContainerImpl::FindInputNodeRegistryKeyForDataType(const FName& InDataTypeName, FNodeRegistryKey& OutKey)
{
UE_LOG(LogMetaSound, Error, TEXT("FRegistryContainerImpl::FindInputNodeRegistryKeyForDataType with these parameters is no longer supported and should not be called. Use the one with EMetasoundFrontendVertexAccessType instead."));
return false;
}
bool FRegistryContainerImpl::FindInputNodeRegistryKeyForDataType(const FName& InDataTypeName, const EMetasoundFrontendVertexAccessType InAccessType, FNodeRegistryKey& OutKey)
{
FMetasoundFrontendClass Class;
switch (InAccessType)
{
case EMetasoundFrontendVertexAccessType::Reference:
{
if (IDataTypeRegistry::Get().GetFrontendInputClass(InDataTypeName, Class))
{
OutKey = NodeRegistryKey::CreateKey(Class.Metadata);
return true;
}
}
break;
case EMetasoundFrontendVertexAccessType::Value:
{
if (IDataTypeRegistry::Get().GetFrontendConstructorInputClass(InDataTypeName, Class))
{
OutKey = NodeRegistryKey::CreateKey(Class.Metadata);
return true;
}
}
break;
default:
case EMetasoundFrontendVertexAccessType::Unset:
{
return false;
}
break;
}
return false;
}
bool FRegistryContainerImpl::FindVariableNodeRegistryKeyForDataType(const FName& InDataTypeName, FNodeRegistryKey& OutKey)
{
FMetasoundFrontendClass Class;
if (IDataTypeRegistry::Get().GetFrontendLiteralClass(InDataTypeName, Class))
{
OutKey = NodeRegistryKey::CreateKey(Class.Metadata);
return true;
}
return false;
}
bool FRegistryContainerImpl::FindOutputNodeRegistryKeyForDataType(const FName& InDataTypeName, FNodeRegistryKey& OutKey)
{
UE_LOG(LogMetaSound, Error, TEXT("FRegistryContainerImpl::FindOutputNodeRegistryKeyForDataType with these parameters is no longer supported and should not be called. Use the one with EMetasoundFrontendVertexAccessType instead."));
return false;
}
bool FRegistryContainerImpl::FindOutputNodeRegistryKeyForDataType(const FName& InDataTypeName, const EMetasoundFrontendVertexAccessType InAccessType, FNodeRegistryKey& OutKey)
{
FMetasoundFrontendClass Class;
switch (InAccessType)
{
case EMetasoundFrontendVertexAccessType::Reference:
{
if (IDataTypeRegistry::Get().GetFrontendOutputClass(InDataTypeName, Class))
{
OutKey = NodeRegistryKey::CreateKey(Class.Metadata);
return true;
}
}
break;
case EMetasoundFrontendVertexAccessType::Value:
{
if (IDataTypeRegistry::Get().GetFrontendConstructorOutputClass(InDataTypeName, Class))
{
OutKey = NodeRegistryKey::CreateKey(Class.Metadata);
return true;
}
}
break;
}
return false;
}
void FRegistryContainerImpl::IterateRegistry(Metasound::FIterateMetasoundFrontendClassFunction InIterFunc, EMetasoundFrontendClassType InClassType) const
{
auto WrappedFunc = [&](const TPair<FNodeRegistryKey, TSharedPtr<INodeRegistryEntry, ESPMode::ThreadSafe>>& Pair)
{
InIterFunc(Pair.Value->GetFrontendClass());
};
if (EMetasoundFrontendClassType::Invalid == InClassType)
{
// Iterate through all classes.
Algo::ForEach(RegisteredNodes, WrappedFunc);
}
else
{
// Only call function on classes of certain type.
auto IsMatchingClassType = [&](const TPair<FNodeRegistryKey, TSharedPtr<INodeRegistryEntry, ESPMode::ThreadSafe>>& Pair)
{
return Pair.Value->GetClassInfo().Type == InClassType;
};
Algo::ForEachIf(RegisteredNodes, IsMatchingClassType, WrappedFunc);
}
}
const INodeRegistryEntry* FRegistryContainerImpl::FindNodeEntry(const FNodeRegistryKey& InKey) const
{
if (const TSharedRef<INodeRegistryEntry, ESPMode::ThreadSafe>* Entry = RegisteredNodes.Find(InKey))
{
return &Entry->Get();
}
return nullptr;
}
const INodeRegistryTemplateEntry* FRegistryContainerImpl::FindNodeTemplateEntry(const FNodeRegistryKey& InKey) const
{
if (const TSharedRef<INodeRegistryTemplateEntry, ESPMode::ThreadSafe>* Entry = RegisteredNodeTemplates.Find(InKey))
{
return &Entry->Get();
}
return nullptr;
}
FNodeRegistryTransaction::FNodeRegistryTransaction(ETransactionType InType, const FNodeClassInfo& InNodeClassInfo, FNodeRegistryTransaction::FTimeType InTimestamp)
: Type(InType)
, NodeClassInfo(InNodeClassInfo)
, Timestamp(InTimestamp)
{
}
FNodeRegistryTransaction::FNodeRegistryTransaction(ETransactionType InType, const FNodeRegistryKey& InKey, const FNodeClassInfo& InNodeClassInfo, FNodeRegistryTransaction::FTimeType InTimestamp)
: FNodeRegistryTransaction(InType, InNodeClassInfo, InTimestamp)
{
}
FNodeRegistryTransaction::ETransactionType FNodeRegistryTransaction::GetTransactionType() const
{
return Type;
}
const FNodeClassInfo& FNodeRegistryTransaction::GetNodeClassInfo() const
{
return NodeClassInfo;
}
FNodeRegistryKey FNodeRegistryTransaction::GetNodeRegistryKey() const
{
return NodeRegistryKey::CreateKey(NodeClassInfo);
}
FNodeRegistryTransaction::FTimeType FNodeRegistryTransaction::GetTimestamp() const
{
return Timestamp;
}
namespace NodeRegistryKey
{
// All registry keys should be created through this function to ensure consistency.
FNodeRegistryKey CreateKey(EMetasoundFrontendClassType InType, const FString& InFullClassName, int32 InMajorVersion, int32 InMinorVersion)
{
using namespace MetasoundFrontendRegistryPrivate;
const FString RegistryKey = FString::Format(TEXT("{0}_{1}_{2}.{3}"), {*GetClassTypeString(InType), *InFullClassName, InMajorVersion, InMinorVersion});
return RegistryKey;
}
const FNodeRegistryKey& GetInvalid()
{
static const FNodeRegistryKey InvalidKey;
return InvalidKey;
}
bool IsValid(const FNodeRegistryKey& InKey)
{
return InKey != GetInvalid();
}
bool IsEqual(const FNodeRegistryKey& InLHS, const FNodeRegistryKey& InRHS)
{
return InLHS == InRHS;
}
bool IsEqual(const FMetasoundFrontendClassMetadata& InLHS, const FMetasoundFrontendClassMetadata& InRHS)
{
if (InLHS.GetClassName() == InRHS.GetClassName())
{
if (InLHS.GetType() == InRHS.GetType())
{
if (InLHS.GetVersion() == InRHS.GetVersion())
{
return true;
}
}
}
return false;
}
bool IsEqual(const FNodeClassInfo& InLHS, const FMetasoundFrontendClassMetadata& InRHS)
{
if (InLHS.ClassName == InRHS.GetClassName())
{
if (InLHS.Type == InRHS.GetType())
{
if (InLHS.Version == InRHS.GetVersion())
{
return true;
}
}
}
return false;
}
FNodeRegistryKey CreateKey(const FNodeClassMetadata& InNodeMetadata)
{
return CreateKey(EMetasoundFrontendClassType::External, InNodeMetadata.ClassName.GetFullName().ToString(), InNodeMetadata.MajorVersion, InNodeMetadata.MinorVersion);
}
FNodeRegistryKey CreateKey(const FMetasoundFrontendClassMetadata& InNodeMetadata)
{
return CreateKey(InNodeMetadata.GetType(), InNodeMetadata.GetClassName().GetFullName().ToString(), InNodeMetadata.GetVersion().Major, InNodeMetadata.GetVersion().Minor);
}
FNodeRegistryKey CreateKey(const FNodeClassInfo& InClassInfo)
{
return CreateKey(InClassInfo.Type, InClassInfo.ClassName.GetFullName().ToString(), InClassInfo.Version.Major, InClassInfo.Version.Minor);
}
}
FNodeClassInfo::FNodeClassInfo(const FMetasoundFrontendClassMetadata& InMetadata)
: ClassName(InMetadata.GetClassName())
, Type(InMetadata.GetType())
, Version(InMetadata.GetVersion())
{
}
FNodeClassInfo::FNodeClassInfo(const FMetasoundFrontendGraphClass& InClass, const FSoftObjectPath& InAssetPath)
: ClassName(InClass.Metadata.GetClassName())
, Type(EMetasoundFrontendClassType::External) // Overridden as it is considered the same as an external class in the registry
, AssetClassID(FGuid(ClassName.Name.ToString()))
, AssetPath(InAssetPath)
, Version(InClass.Metadata.GetVersion())
{
ensure(!AssetPath.IsNull());
#if WITH_EDITORONLY_DATA
for (const FMetasoundFrontendClassInput& Input : InClass.Interface.Inputs)
{
InputTypes.Add(Input.TypeName);
}
for (const FMetasoundFrontendClassOutput& Output : InClass.Interface.Outputs)
{
OutputTypes.Add(Output.TypeName);
}
bIsPreset = InClass.PresetOptions.bIsPreset;
#endif // WITH_EDITORONLY_DATA
}
} // namespace Frontend
} // namespace Metasound
FMetasoundFrontendRegistryContainer* FMetasoundFrontendRegistryContainer::Get()
{
return &Metasound::Frontend::FRegistryContainerImpl::Get();
}
void FMetasoundFrontendRegistryContainer::ShutdownMetasoundFrontend()
{
Metasound::Frontend::FRegistryContainerImpl::Shutdown();
}
Metasound::Frontend::FNodeRegistryKey FMetasoundFrontendRegistryContainer::GetRegistryKey(const FNodeClassMetadata& InNodeMetadata)
{
return Metasound::Frontend::NodeRegistryKey::CreateKey(InNodeMetadata);
}
Metasound::Frontend::FNodeRegistryKey FMetasoundFrontendRegistryContainer::GetRegistryKey(const FMetasoundFrontendClassMetadata& InNodeMetadata)
{
return Metasound::Frontend::NodeRegistryKey::CreateKey(InNodeMetadata);
}
Metasound::Frontend::FNodeRegistryKey FMetasoundFrontendRegistryContainer::GetRegistryKey(const FNodeClassInfo& InClassInfo)
{
return Metasound::Frontend::NodeRegistryKey::CreateKey(InClassInfo);
}
bool FMetasoundFrontendRegistryContainer::GetFrontendClassFromRegistered(const FNodeRegistryKey& InKey, FMetasoundFrontendClass& OutClass)
{
FMetasoundFrontendRegistryContainer* Registry = FMetasoundFrontendRegistryContainer::Get();
if (ensure(nullptr != Registry))
{
return Registry->FindFrontendClassFromRegistered(InKey, OutClass);
}
return false;
}
bool FMetasoundFrontendRegistryContainer::GetNodeClassInfoFromRegistered(const FNodeRegistryKey& InKey, FNodeClassInfo& OutInfo)
{
if (FMetasoundFrontendRegistryContainer* Registry = FMetasoundFrontendRegistryContainer::Get())
{
return Registry->FindNodeClassInfoFromRegistered(InKey, OutInfo);
}
return false;
}
bool FMetasoundFrontendRegistryContainer::GetInputNodeRegistryKeyForDataType(const FName& InDataTypeName, FNodeRegistryKey& OutKey)
{
UE_LOG(LogMetaSound, Error, TEXT("FMetasoundFrontendRegistryContainer::GetInputNodeRegistryKeyForDataType with these parameters is no longer supported and should not be called. Use the one with EMetasoundFrontendVertexAccessType instead."));
return false;
}
bool FMetasoundFrontendRegistryContainer::GetInputNodeRegistryKeyForDataType(const FName& InDataTypeName, const EMetasoundFrontendVertexAccessType InAccessType, FNodeRegistryKey& OutKey)
{
if (FMetasoundFrontendRegistryContainer* Registry = FMetasoundFrontendRegistryContainer::Get())
{
return Registry->FindInputNodeRegistryKeyForDataType(InDataTypeName, InAccessType, OutKey);
}
return false;
}
bool FMetasoundFrontendRegistryContainer::GetVariableNodeRegistryKeyForDataType(const FName& InDataTypeName, FNodeRegistryKey& OutKey)
{
if (FMetasoundFrontendRegistryContainer* Registry = FMetasoundFrontendRegistryContainer::Get())
{
return Registry->FindVariableNodeRegistryKeyForDataType(InDataTypeName, OutKey);
}
return false;
}
bool FMetasoundFrontendRegistryContainer::GetOutputNodeRegistryKeyForDataType(const FName& InDataTypeName, FNodeRegistryKey& OutKey)
{
UE_LOG(LogMetaSound, Error, TEXT("FMetasoundFrontendRegistryContainer::GetOutputNodeRegistryKeyForDataType with these parameters is no longer supported and should not be called. Use the one with EMetasoundFrontendVertexAccessType instead."));
return false;
}
bool FMetasoundFrontendRegistryContainer::GetOutputNodeRegistryKeyForDataType(const FName& InDataTypeName, const EMetasoundFrontendVertexAccessType InVertexAccessType, FNodeRegistryKey& OutKey)
{
if (FMetasoundFrontendRegistryContainer* Registry = FMetasoundFrontendRegistryContainer::Get())
{
return Registry->FindOutputNodeRegistryKeyForDataType(InDataTypeName, InVertexAccessType, OutKey);
}
return false;
}