I imitated this link to create a node, https://dev.epicgames.com/community/learning/tutorials/ry7p/unreal-engine-creating-metasound-nodes-in-c-quickstart
and then put it in the plug-in of my project. Next, how should I trigger the node I created? I tried to search in metasound, but I couldn’t find it…
#pragma once
#include "MetasoundExecutableOperator.h" // TExecutableOperator class
#include "MetasoundPrimitives.h" // ReadRef and WriteRef descriptions for bool, int32, float, and string
#include "MetasoundNodeRegistrationMacro.h" // METASOUND_LOCTEXT and METASOUND_REGISTER_NODE macros
#include "MetasoundStandardNodesNames.h" // StandardNodes namespace
#include "MetasoundFacade.h" // FNodeFacade class, eliminates the need for a fair amount of boilerplate code
#include "MetasoundParamHelper.h"
#include "MetasoundTrigger.h"
#define LOCTEXT_NAMESPACE "MetasoundStandardNodes_TutorialNode"
namespace Metasound
{
namespace TutorialNodeNames
{
METASOUND_PARAM(InputAValue, "A", "Input value A.");
METASOUND_PARAM(InputBValue, "B", "Input value B.");
METASOUND_PARAM(OutputValue, "Sum of A and B", "The sum of A and B.");
}
class FTutorialOperator : public TExecutableOperator<FTutorialOperator>
{
public:
FTutorialOperator(
const FFloatReadRef& InAValue,
const FFloatReadRef& InBValue)
: InputA(InAValue)
, InputB(InBValue)
, TutorialNodeOutput(FFloatWriteRef::CreateNew(*InputA + *InputB))
{
}
static const FVertexInterface& DeclareVertexInterface();
static const FNodeClassMetadata& GetNodeInfo();
virtual FDataReferenceCollection GetInputs() const override;
virtual FDataReferenceCollection GetOutputs() const override;
static TUniquePtr<IOperator> CreateOperator(const FCreateOperatorParams& InParams, FBuildErrorArray& OutErrors);
// Primary node functionality
void Execute();
private:
// Inputs
FFloatReadRef InputA;
FFloatReadRef InputB;
// Outputs
FFloatWriteRef TutorialNodeOutput;
};
class FTutorialNode : public FNodeFacade
{
public:
FTutorialNode(const FNodeInitData& InitData)
: FNodeFacade(InitData.InstanceName, InitData.InstanceID, TFacadeOperatorClass<FTutorialOperator>())
{
}
};
}
#include "MetaSound/TutorialNode.h"
namespace Metasound
{
// Helper function for constructing vertex interface
const FVertexInterface& FTutorialOperator::DeclareVertexInterface()
{
using namespace TutorialNodeNames;
static const FVertexInterface Interface(
FInputVertexInterface(
TInputDataVertex<float>(METASOUND_GET_PARAM_NAME_AND_METADATA(InputAValue)),
TInputDataVertex<float>(METASOUND_GET_PARAM_NAME_AND_METADATA(InputBValue))
),
FOutputVertexInterface(
TOutputDataVertex<float>(METASOUND_GET_PARAM_NAME_AND_METADATA(OutputValue))
)
);
return Interface;
}
const FNodeClassMetadata& FTutorialOperator::GetNodeInfo()
{
auto CreateNodeClassMetadata = []() -> FNodeClassMetadata
{
FVertexInterface NodeInterface = DeclareVertexInterface();
FNodeClassMetadata Metadata;
Metadata.ClassName = { "UE", "Tutorial Node", "Audio" };
Metadata.MajorVersion = 1;
Metadata.MinorVersion = 0;
Metadata.DisplayName = METASOUND_LOCTEXT("TutorialNodeDisplayName", "Tutorial Node");
Metadata.Description = METASOUND_LOCTEXT("TutorialNodeDesc", "A simple node to demonstrate how to create new MetaSound nodes in C++. Adds two floats together");
Metadata.Author = PluginAuthor;
Metadata.PromptIfMissing = PluginNodeMissingPrompt;
Metadata.DefaultInterface = NodeInterface;
Metadata.CategoryHierarchy = {};
FNodeDisplayStyle{};
return Metadata;
};
static const FNodeClassMetadata Metadata = CreateNodeClassMetadata();
return Metadata;
}
FDataReferenceCollection FTutorialOperator::GetInputs() const
{
using namespace TutorialNodeNames;
FDataReferenceCollection InputDataReferences;
InputDataReferences.AddDataReadReference(METASOUND_GET_PARAM_NAME(InputAValue), InputA);
InputDataReferences.AddDataReadReference(METASOUND_GET_PARAM_NAME(InputBValue), InputB);
return InputDataReferences;
}
FDataReferenceCollection FTutorialOperator::GetOutputs() const
{
using namespace TutorialNodeNames;
FDataReferenceCollection OutputDataReferences;
OutputDataReferences.AddDataReadReference(METASOUND_GET_PARAM_NAME(OutputValue), TutorialNodeOutput);
return OutputDataReferences;
}
TUniquePtr<IOperator> FTutorialOperator::CreateOperator(const FCreateOperatorParams& InParams, FBuildErrorArray& OutErrors)
{
using namespace TutorialNodeNames;
const Metasound::FDataReferenceCollection& InputCollection = InParams.InputDataReferences;
const Metasound::FInputVertexInterface& InputInterface = DeclareVertexInterface().GetInputInterface();
TDataReadReference<float> InputA = InputCollection.GetDataReadReferenceOrConstructWithVertexDefault<float>(InputInterface, METASOUND_GET_PARAM_NAME(InputAValue), InParams.OperatorSettings);
TDataReadReference<float> InputB = InputCollection.GetDataReadReferenceOrConstructWithVertexDefault<float>(InputInterface, METASOUND_GET_PARAM_NAME(InputBValue), InParams.OperatorSettings);
return MakeUnique<FTutorialOperator>(InputA, InputB);
}
void FTutorialOperator::Execute()
{
*TutorialNodeOutput = *InputA + *InputB;
}
METASOUND_REGISTER_NODE(FTutorialNode);
}
#undef LOCTEXT_NAMESPACE