Skip to content
Snippets Groups Projects
Commit 671b944c authored by jsiegle's avatar jsiegle
Browse files

Update ProcessorGraph from spikesorting branch

parent 4c965cf5
No related branches found
No related tags found
No related merge requests found
......@@ -27,7 +27,6 @@
#include "AudioNode.h"
#include "LfpDisplayNode.h"
#include "LfpTriggeredAverageNode.h"
#include "SpikeDisplayNode.h"
#include "EventNode.h"
#include "FilterNode.h"
......@@ -68,8 +67,10 @@ ProcessorGraph::ProcessorGraph() : currentNodeId(100)
}
ProcessorGraph::~ProcessorGraph() { }
ProcessorGraph::~ProcessorGraph()
{
}
void ProcessorGraph::createDefaultNodes()
{
......@@ -123,12 +124,13 @@ void ProcessorGraph::updatePointers()
getRecordNode()->setUIComponent(getUIComponent());
}
void* ProcessorGraph::createNewProcessor(String& description, int id)
void* ProcessorGraph::createNewProcessor(String& description, int id)//,
{
GenericProcessor* processor = createProcessorFromDescription(description);
//int id = currentNodeId++;
// int id = currentNodeId++;
if (processor != 0)
{
......@@ -156,33 +158,18 @@ void* ProcessorGraph::createNewProcessor(String& description, int id)
void ProcessorGraph::clearSignalChain()
{
int n = 0;
Array<GenericProcessor*> processors = getListOfProcessors();
while (getNumNodes() > 4)
for (int i = 0; i < processors.size(); i++)
{
Node* node = getNode(n);
int nodeId = node->nodeId;
if (nodeId != OUTPUT_NODE_ID &&
nodeId != AUDIO_NODE_ID &&
nodeId != RECORD_NODE_ID &&
nodeId != RESAMPLING_NODE_ID)
{
GenericProcessor* p =(GenericProcessor*) node->getProcessor();
removeProcessor(p);
}
else
{
n++;
}
removeProcessor(processors[i]);
}
}
void ProcessorGraph::changeListenerCallback(ChangeBroadcaster* source)
{
refreshColors();
refreshColors();
}
......@@ -290,162 +277,201 @@ void ProcessorGraph::updateConnections(Array<SignalChainTabButton*, CriticalSect
clearConnections(); // clear processor graph
std::cout << "Updating connections:" << std::endl;
std::cout << std::endl;
std::cout << std::endl;
Array<GenericProcessor*> splitters;
// GenericProcessor* activeSplitter = nullptr;
for (int n = 0; n < tabs.size(); n++)
for (int n = 0; n < tabs.size(); n++) // cycle through the tabs
{
std::cout << "Signal chain " << n << std::endl;
std::cout << "Signal chain: " << n << std::endl;
std::cout << std::endl;
GenericEditor* sourceEditor = (GenericEditor*) tabs[n]->getEditor();
GenericProcessor* source = (GenericProcessor*) sourceEditor->getProcessor();
while (source != 0)// && destEditor->isEnabled())
while (source != nullptr)// && destEditor->isEnabled())
{
std::cout << "Source node: " << source->getName() << ", ";
std::cout << "Source node: " << source->getName() << "." << std::endl;
GenericProcessor* dest = (GenericProcessor*) source->getDestNode();
if (dest != 0)
if (source->enabledState())
{
std::cout << "Dest node: " << dest->getName() << std::endl;
if (dest->isMerger()) // move it forward by one
{
dest = dest->getDestNode();
}
else if (dest->isSplitter())
// add the connections to audio and record nodes if necessary
if (!(source->isSink() ||
source->isSplitter() ||
source->isMerger() ||
source->isUtility())
&& !(source->wasConnected))
{
if (!dest->wasConnected)
splitters.add(dest);
dest = dest->getDestNode();
std::cout << " Connecting to audio and record nodes." << std::endl;
connectProcessorToAudioAndRecordNodes(source);
} else {
std::cout << " NOT connecting to audio and record nodes." << std::endl;
}
}
else
{
std::cout << "no dest node." << std::endl;
}
if (source->enabledState())
{
// add the connections to audio and record nodes if necessary
if (!(source->isSink() ||
source->isSplitter() || source->isMerger() || source->isUtility()) && !(source->wasConnected))
if (dest != nullptr)
{
std::cout << " Connecting to audio and record nodes." << std::endl;
//source->setStartChannel(getAudioNode()->getNextChannel(false));
while (dest->isMerger()) // find the next dest that's not a merger
{
dest = dest->getDestNode();
if (dest == nullptr)
break;
}
for (int chan = 0; chan < source->getNumOutputs(); chan++)
if (dest != nullptr)
{
while (dest->isSplitter())
{
if (!dest->wasConnected)
{
if (!splitters.contains(dest))
{
splitters.add(dest);
dest->switchIO(0); // go down first path
} else {
int splitterIndex = splitters.indexOf(dest);
splitters.remove(splitterIndex);
dest->switchIO(1); // go down second path
dest->wasConnected = true; // make sure we don't re-use this splitter
}
}
dest = dest->getDestNode();
if (dest == nullptr)
break;
}
getAudioNode()->addInputChannel(source, chan);
getAudioNode()->settings.sampleRate = source->getSampleRate(); // THIS IS A HACK TO MAKE SURE AUDIO NODE KNOWS WHAT THE SAMPLE RATE SHOULD BE
if (dest != nullptr)
{
// std::cout << "Connecting to audio channel: " <<
// getAudioNode()->getNextChannel(false) << std::endl;
if (dest->enabledState())
{
connectProcessors(source, dest);
}
}
//getAudioNode()->enableCurrentChannel(source->audioStatus(chan));
} else {
std::cout << " No dest node." << std::endl;
}
addConnection(source->getNodeId(), // sourceNodeID
chan, // sourceNodeChannelIndex
AUDIO_NODE_ID, // destNodeID
getAudioNode()->getNextChannel(true)); // destNodeChannelIndex
// add 2 to account for 2 output channels
} else {
std::cout << " No dest node." << std::endl;
}
}
std::cout << std::endl;
//std::cout << getAudioNode()->getNextChannel(false) << " ";
source->wasConnected = true;
source = dest; // switch source and dest
getRecordNode()->addInputChannel(source, chan);
if (source == nullptr && splitters.size() > 0)
{
// std::cout << "Connecting to record channel: " <<
// getRecordNode()->getNextChannel(false) << std::endl;
source = splitters.getLast();
GenericProcessor* newSource;// = source->getSourceNode();
while (source->isSplitter() || source->isMerger())
{
newSource = source->getSourceNode();
newSource->setPathToProcessor(source);
source = newSource;
}
addConnection(source->getNodeId(), // sourceNodeID
chan, // sourceNodeChannelIndex
RECORD_NODE_ID, // destNodeID
getRecordNode()->getNextChannel(true)); // destNodeChannelIndex
// source = splitters.getFirst()->getSourceNode(); // dest is now the splitter
//splitters.remove(0); // take it out of the array
//dest->switchIO(1); // switch to the other destination
//dest->wasConnected = true; // don't want to re-add splitter
// source = dest->getSourceNode(); // splitter is now source
}
}
} // end while source != 0
} // end "tabs" for loop
// connect event channel
addConnection(source->getNodeId(), // sourceNodeID
midiChannelIndex, // sourceNodeChannelIndex
RECORD_NODE_ID, // destNodeID
midiChannelIndex); // destNodeChannelIndex
} // end method
// connect event channel
addConnection(source->getNodeId(), // sourceNodeID
midiChannelIndex, // sourceNodeChannelIndex
AUDIO_NODE_ID, // destNodeID
midiChannelIndex); // destNodeChannelIndex
void ProcessorGraph::connectProcessors(GenericProcessor* source, GenericProcessor* dest)
{
if (source == nullptr || dest == nullptr)
return;
getRecordNode()->addInputChannel(source, midiChannelIndex);
std::cout << " Connecting " << source->getName() << " " << source->getNodeId(); //" channel ";
std::cout << " to " << dest->getName() << " " << dest->getNodeId() << std::endl;
}
// 1. connect continuous channels
for (int chan = 0; chan < source->getNumOutputs(); chan++)
{
//std::cout << chan << " ";
std::cout << std::endl;
addConnection(source->getNodeId(), // sourceNodeID
chan, // sourceNodeChannelIndex
dest->getNodeId(), // destNodeID
dest->getNextChannel(true)); // destNodeChannelIndex
}
if (dest != 0)
{
// std::cout << " Connecting " << source->getName() <<
// " event channel to " <<
// dest->getName() << std::endl;
if (dest->enabledState())
std::cout << " OK." << std::endl;
else
std::cout << " Not OK." << std::endl;
// 2. connect event channel
addConnection(source->getNodeId(), // sourceNodeID
midiChannelIndex, // sourceNodeChannelIndex
dest->getNodeId(), // destNodeID
midiChannelIndex); // destNodeChannelIndex
if (dest->enabledState())
{
}
std::cout << " Connecting " << source->getName() << " channel ";
void ProcessorGraph::connectProcessorToAudioAndRecordNodes(GenericProcessor* source)
{
for (int chan = 0; chan < source->getNumOutputs(); chan++)
{
std::cout << chan << " ";
if (source == nullptr)
return;
addConnection(source->getNodeId(), // sourceNodeID
chan, // sourceNodeChannelIndex
dest->getNodeId(), // destNodeID
dest->getNextChannel(true)); // destNodeChannelIndex
}
for (int chan = 0; chan < source->getNumOutputs(); chan++)
{
std::cout << " to " << dest->getName() << std::endl;
getAudioNode()->addInputChannel(source, chan);
std::cout << " Connecting " << source->getName() <<
" event channel to " <<
dest->getName() << std::endl;
// THIS IS A HACK TO MAKE SURE AUDIO NODE KNOWS WHAT THE SAMPLE RATE SHOULD BE
// IT CAN CAUSE PROBLEMS IF THE SAMPLE RATE VARIES ACROSS PROCESSORS
getAudioNode()->settings.sampleRate = source->getSampleRate();
// connect event channel
addConnection(source->getNodeId(), // sourceNodeID
midiChannelIndex, // sourceNodeChannelIndex
dest->getNodeId(), // destNodeID
midiChannelIndex); // destNodeChannelIndex
addConnection(source->getNodeId(), // sourceNodeID
chan, // sourceNodeChannelIndex
AUDIO_NODE_ID, // destNodeID
getAudioNode()->getNextChannel(true)); // destNodeChannelIndex
}
getRecordNode()->addInputChannel(source, chan);
}
}
addConnection(source->getNodeId(), // sourceNodeID
chan, // sourceNodeChannelIndex
RECORD_NODE_ID, // destNodeID
getRecordNode()->getNextChannel(true)); // destNodeChannelIndex
source->wasConnected = true;
source = dest; // switch source and dest
}
if (source == 0 && splitters.size() > 0)
{
dest = splitters.getFirst(); // dest is now the splitter
splitters.remove(0); // take it out of the
dest->switchIO(); // switch to the other destination
dest->wasConnected = true; // don't want to re-add splitter
source = dest->getSourceNode(); // splitter is now source
}
// connect event channel
addConnection(source->getNodeId(), // sourceNodeID
midiChannelIndex, // sourceNodeChannelIndex
RECORD_NODE_ID, // destNodeID
midiChannelIndex); // destNodeChannelIndex
// connect event channel
addConnection(source->getNodeId(), // sourceNodeID
midiChannelIndex, // sourceNodeChannelIndex
AUDIO_NODE_ID, // destNodeID
midiChannelIndex); // destNodeChannelIndex
} // end while source != 0
} // end "tabs" for loop
} // end method
getRecordNode()->addInputChannel(source, midiChannelIndex);
}
GenericProcessor* ProcessorGraph::createProcessorFromDescription(String& description)
{
......@@ -491,7 +517,12 @@ GenericProcessor* ProcessorGraph::createProcessorFromDescription(String& descrip
{
processor = new FileReader();
std::cout << "Creating a new file reader." << std::endl;
}
}
else if (subProcessorType.equalsIgnoreCase("Network Events"))
{
std::cout << "Creating a new network events source." << std::endl;
processor = new NetworkEvents(zmqcontext);
}
else if (subProcessorType.equalsIgnoreCase("Serial Port"))
{
processor = new SerialInput();
......@@ -499,6 +530,7 @@ GenericProcessor* ProcessorGraph::createProcessorFromDescription(String& descrip
}
sendActionMessage("New source node created.");
......@@ -543,8 +575,13 @@ GenericProcessor* ProcessorGraph::createProcessorFromDescription(String& descrip
{
std::cout << "Creating a new channel mapping node." << std::endl;
processor = new ChannelMappingNode();
} else if (subProcessorType.equalsIgnoreCase("Eye Tracking"))
{
std::cout << "Creating a ISCAN source." << std::endl;
processor = new ISCANnode();
}
sendActionMessage("New filter node created.");
}
......@@ -577,6 +614,10 @@ GenericProcessor* ProcessorGraph::createProcessorFromDescription(String& descrip
sendActionMessage("New record controller created.");
}else if (subProcessorType.equalsIgnoreCase("Advancers"))
{
std::cout << "Creating a new advancers node." << std::endl;
processor = new AdvancerNode();
}
}
......@@ -592,16 +633,25 @@ GenericProcessor* ProcessorGraph::createProcessorFromDescription(String& descrip
// processor->setDataViewport(getDataViewport());
//processor->setUIComponent(UI);
}
else if (subProcessorType.equalsIgnoreCase("LFP Trig. Avg."))
{
std::cout << "Creating an LfpTrigAvgNode." << std::endl;
processor = new LfpTriggeredAverageNode();
}
// else if (subProcessorType.equalsIgnoreCase("LFP Trig. Avg."))
// {
// std::cout << "Creating an LfpTrigAvgNode." << std::endl;
// processor = new LfpTriggeredAverageNode();
// }
else if (subProcessorType.equalsIgnoreCase("Spike Viewer"))
{
std::cout << "Creating a SpikeDisplayNode." << std::endl;
processor = new SpikeDisplayNode();
}
else if (subProcessorType.equalsIgnoreCase("PSTH"))
{
std::cout << "Creating a PSTH sink." << std::endl;
processor = new PeriStimulusTimeHistogramNode();
} else if (subProcessorType.equalsIgnoreCase("Network Sink"))
{
std::cout << "Creating a Network sink." << std::endl;
processor = new NetworkSinkNode(zmqcontext);
}
else if (subProcessorType.equalsIgnoreCase("WiFi Output"))
{
......@@ -789,4 +839,4 @@ RecordNode* ProcessorGraph::getRecordNode()
Node* node = getNodeForId(RECORD_NODE_ID);
return (RecordNode*) node->getProcessor();
}
\ No newline at end of file
}
......@@ -61,7 +61,7 @@ public:
GenericProcessor* createProcessorFromDescription(String& description);
void removeProcessor(GenericProcessor* processor);
Array<GenericProcessor*> getListOfProcessors();
void clearSignalChain();
bool enableProcessors();
......@@ -83,8 +83,6 @@ public:
void setRecordState(bool);
Array<GenericProcessor*> getListOfProcessors();
void refreshColors();
private:
......@@ -103,6 +101,9 @@ private:
void clearConnections();
void connectProcessors(GenericProcessor* source, GenericProcessor* dest);
void connectProcessorToAudioAndRecordNodes(GenericProcessor* source);
};
......
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment