tracktion-engine 3.0-10-g034fdde4aa5
Tracktion Engine — High level data model for audio applications

« « « Anklang Documentation
Loading...
Searching...
No Matches
tracktion_InsertSendNode.cpp
Go to the documentation of this file.
1 /*
2 ,--. ,--. ,--. ,--.
3 ,-' '-.,--.--.,--,--.,---.| |,-.,-' '-.`--' ,---. ,--,--, Copyright 2024
4 '-. .-'| .--' ,-. | .--'| /'-. .-',--.| .-. || \ Tracktion Software
5 | | | | \ '-' \ `--.| \ \ | | | |' '-' '| || | Corporation
6 `---' `--' `--`--'`---'`--'`--' `---' `--' `---' `--''--' www.tracktion.com
7
8 Tracktion Engine uses a GPL/commercial licence - see LICENCE.md for details.
9*/
10
11namespace tracktion { inline namespace engine
12{
13
14InsertNode::InsertNode (std::unique_ptr<Node> input_, InsertPlugin& ip, std::unique_ptr<Node> returnNode_, SampleRateAndBlockSize info)
15 : owner (ip), plugin (ip),
16 input (std::move (input_)),
17 returnNode (std::move (returnNode_))
18{
19 assert (input);
20 assert (returnNode);
21
22 setOptimisations ({ tracktion::graph::ClearBuffers::no,
23 tracktion::graph::AllocateAudioBuffer::no });
24
25 plugin->baseClassInitialise ({ TimePosition(), info.sampleRate, info.blockSize });
26 isInitialised = true;
27}
28
29InsertNode::~InsertNode()
30{
31 if (isInitialised && ! plugin->baseClassNeedsInitialising())
32 plugin->baseClassDeinitialise();
33}
34
35TransformResult InsertNode::transform (Node&, const std::vector<Node*>& postOrderedNodes, TransformCache&)
36{
37 if (sendNode)
38 return TransformResult::none;
39
40 for (auto n : postOrderedNodes)
41 {
42 if (auto in = dynamic_cast<InsertSendNode*> (n))
43 {
44 if (&in->getInsert() == plugin.get())
45 {
46 sendNode = in;
47 return TransformResult::connectionsMade;
48 }
49 }
50 }
51
52 return TransformResult::none;
53}
54
55tracktion::graph::NodeProperties InsertNode::getNodeProperties()
56{
57 auto props = returnNode->getNodeProperties();
58 props.latencyNumSamples += owner.getLatencyNumSamples();
59
60 if (sendNode)
61 props.latencyNumSamples += sendNode->getLatencyAtInput();
62
63 return props;
64}
65
66std::vector<Node*> InsertNode::getDirectInputNodes()
67{
68 return { returnNode.get() };
69}
70
71void InsertNode::prepareToPlay (const tracktion::graph::PlaybackInitialisationInfo&)
72{
73}
74
75bool InsertNode::isReadyToProcess()
76{
77 return returnNode->hasProcessed();
78}
79
80void InsertNode::process (ProcessContext& pc)
81{
82 auto buffers = returnNode->getProcessedOutput();
83 setAudioOutput (returnNode.get(), buffers.audio.getStart (pc.buffers.audio.getNumFrames()));
84 pc.buffers.midi.copyFrom (buffers.midi);
85}
86
87
88//==============================================================================
89//==============================================================================
90InsertSendNode::InsertSendNode (InsertPlugin& ip)
91 : owner (ip), plugin (ip)
92{
93}
94
95int InsertSendNode::getLatencyAtInput()
96{
97 return input ? input->getNodeProperties().latencyNumSamples
98 : 0;
99}
100
101//==============================================================================
103{
104 if (input)
105 {
106 auto props = input->getNodeProperties();
107 props.latencyNumSamples = std::numeric_limits<int>::min();
108
109 return props;
110 }
111
113 props.hasAudio = owner.hasAudio();
114 props.hasMidi = owner.hasMidi();
115 props.numberOfChannels = props.hasAudio ? 2 : 0;
116 props.latencyNumSamples = owner.getLatencyNumSamples();
117
118 return props;
119}
120
122{
123 if (input)
124 return { input };
125
126 return {};
127}
128
130{
131 if (input)
132 return TransformResult::none;
133
134 for (auto n : postOrderedNodes)
135 {
136 if (auto in = dynamic_cast<InsertNode*> (n))
137 {
138 if (&in->getInsert() == plugin.get())
139 {
140 input = &in->getInputNode();
141 return TransformResult::connectionsMade;
142 }
143 }
144 }
145
146 return TransformResult::none;
147}
148
150{
151 if (input)
152 setOptimisations ({ tracktion::graph::ClearBuffers::no,
153 tracktion::graph::AllocateAudioBuffer::no });
154}
155
157{
158 return input == nullptr || input->hasProcessed();
159}
160
162{
163 if (! input)
164 return;
165
166 auto buffers = input->getProcessedOutput();
167 setAudioOutput (input, buffers.audio.getStart (pc.buffers.audio.getNumFrames()));
168 pc.buffers.midi.copyFrom (buffers.midi);
169}
170
171}} // namespace tracktion { inline namespace engine
assert
ReferencedType * get() const noexcept
bool hasMidi() const
Returns true if either the send or return types are MIDI.
bool hasAudio() const
Returns true if either the send or return types are audio.
The send node picks up audio/MIDI data from the InsertPlugin and then its output will be sent to the ...
void process(ProcessContext &) override
Called when the node is to be processed.
TransformResult transform(Node &, const std::vector< Node * > &, TransformCache &) override
Called after construction to give the node a chance to modify its topology.
std::vector< Node * > getDirectInputNodes() override
Should return all the inputs directly feeding in to this node.
tracktion::graph::NodeProperties getNodeProperties() override
Should return the properties of the node.
bool isReadyToProcess() override
Should return true when this node is ready to be processed.
void prepareToPlay(const tracktion::graph::PlaybackInitialisationInfo &) override
Called once before playback begins for each node.
Main graph Node processor class.
void setAudioOutput(Node *sourceNode, const choc::buffer::ChannelArrayView< float > &)
This can be called during your process function to set a view to the output.
virtual NodeProperties getNodeProperties()=0
Should return the properties of the node.
void setOptimisations(NodeOptimisations)
This can be called to provide some hints about allocating or playing back a Node to improve efficienc...
bool hasProcessed() const
Returns true if this node has processed and its outputs can be retrieved.
AudioAndMidiBuffer getProcessedOutput()
Returns the processed audio and MIDI output.
Struct to describe a single iteration of a process call.
T min(T... args)
T move(T... args)
TransformResult
Enum to signify the result of the transform function.
Holds some really basic properties of a node.
Passed into Nodes when they are being initialised, to give them useful contextual information that th...