diff --git a/Source/Processors/ProcessorGraph.cpp b/Source/Processors/ProcessorGraph.cpp index c0c64686e30eaa58021b9ad2ccc2d870cf6a7ec5..bcd2a84a15be248335bf223654360f422c958a05 100644 --- a/Source/Processors/ProcessorGraph.cpp +++ b/Source/Processors/ProcessorGraph.cpp @@ -123,12 +123,12 @@ void ProcessorGraph::updatePointers() getRecordNode()->setUIComponent(getUIComponent()); } -void* ProcessorGraph::createNewProcessor(String& description) +void* ProcessorGraph::createNewProcessor(String& description, int id) { GenericProcessor* processor = createProcessorFromDescription(description); - int id = currentNodeId++; + //int id = currentNodeId++; if (processor != 0) { @@ -182,6 +182,12 @@ void ProcessorGraph::clearSignalChain() void ProcessorGraph::changeListenerCallback(ChangeBroadcaster* source) { + refreshColors(); + +} + +void ProcessorGraph::refreshColors() +{ for (int i = 0; i < getNumNodes(); i++) { Node* node = getNode(i); @@ -198,7 +204,6 @@ void ProcessorGraph::changeListenerCallback(ChangeBroadcaster* source) e->refreshColors(); } } - } void ProcessorGraph::restoreParameters() diff --git a/Source/Processors/ProcessorGraph.h b/Source/Processors/ProcessorGraph.h index ef0ae08e9589ff69b0ecd90e3e8e702e09fa51b7..3ea84eb4d132d6c57baeb2d686c0f955b98fd2fe 100644 --- a/Source/Processors/ProcessorGraph.h +++ b/Source/Processors/ProcessorGraph.h @@ -57,7 +57,7 @@ public: ProcessorGraph(); ~ProcessorGraph(); - void* createNewProcessor(String& description); + void* createNewProcessor(String& description, int id); GenericProcessor* createProcessorFromDescription(String& description); void removeProcessor(GenericProcessor* processor); @@ -85,6 +85,8 @@ public: Array<GenericProcessor*> getListOfProcessors(); + void refreshColors(); + private: int currentNodeId; diff --git a/Source/UI/EditorViewport.cpp b/Source/UI/EditorViewport.cpp index ab24b75bd762842a73e75c359981e44a2fb8649f..ea774886ff3bbd3b867731588522550dc803e376 100755 --- a/Source/UI/EditorViewport.cpp +++ b/Source/UI/EditorViewport.cpp @@ -67,6 +67,9 @@ EditorViewport::EditorViewport() addAndMakeVisible(rightButton); addAndMakeVisible(leftButton); + currentId = 100; + maxId = 100; + } EditorViewport::~EditorViewport() @@ -113,14 +116,14 @@ void EditorViewport::paint(Graphics& g) float insertionX = (float)(borderSize) * 2.5 + (float) tabSize; int n; - for (n = 0; n < insertionPoint; n++) + for (n = leftmostEditor; n < insertionPoint; n++) { insertionX += editorArray[n]->getWidth(); } - if (n > 1) - insertionX += borderSize*(n-1); + if (n - leftmostEditor > 1) + insertionX += borderSize*(n-leftmostEditor-1); g.setColour(Colours::yellow); g.drawLine(insertionX, (float) borderSize, @@ -131,13 +134,18 @@ void EditorViewport::paint(Graphics& g) int insertionX = tabSize + borderSize; g.setColour(Colours::darkgrey); - int x = insertionX + 19; + int x = insertionX + 15; int y = borderSize + 2; //int w = 30; //int h = getHeight() - 2*(borderSize+2); - g.drawImageAt(sourceDropImage, x, y); - + if (editorArray.size() > 0) + { + if (!editorArray[0]->getProcessor()->isSource()) + g.drawImageAt(sourceDropImage, x, y); + } else { + g.drawImageAt(sourceDropImage, x, y); + } } bool EditorViewport::isInterestedInDragSource(const SourceDetails& dragSourceDetails) @@ -180,7 +188,7 @@ void EditorViewport::itemDragMove(const SourceDetails& dragSourceDetails) int leftEdge; int centerPoint; - for (int n = 0; n < editorArray.size(); n++) + for (int n = leftmostEditor; n < editorArray.size(); n++) { leftEdge = editorArray[n]->getX(); centerPoint = leftEdge + (editorArray[n]->getWidth())/2; @@ -230,7 +238,7 @@ void EditorViewport::itemDropped(const SourceDetails& dragSourceDetails) /// needed to remove const cast --> should be a better way to do this //String description = sourceDescription.substring(0); - GenericEditor* activeEditor = (GenericEditor*) getProcessorGraph()->createNewProcessor(description);//, source, dest); + GenericEditor* activeEditor = (GenericEditor*) getProcessorGraph()->createNewProcessor(description, currentId);//, source, dest); std::cout << "Active editor: " << activeEditor << std::endl; @@ -263,6 +271,9 @@ void EditorViewport::itemDropped(const SourceDetails& dragSourceDetails) getGraphViewer()->addNode(activeEditor); repaint(); + + currentId++; + } } @@ -307,6 +318,18 @@ void EditorViewport::makeEditorVisible(GenericEditor* editor, bool highlight, bo if (highlight) editor->highlight(); + while (!editor->isVisible()) + { + if (leftmostEditor < editorArray.indexOf(editor)) + leftmostEditor++; + else + leftmostEditor--; + + refreshEditors(); + } + + repaint(); + } void EditorViewport::deleteNode(GenericEditor* editor) @@ -331,6 +354,8 @@ void EditorViewport::deleteNode(GenericEditor* editor) + repaint(); + } } @@ -654,13 +679,31 @@ void EditorViewport::mouseDown(const MouseEvent& e) for (int i = 0; i < editorArray.size(); i++) { - if (e.eventComponent == editorArray[i] && e.y < 22) - // event must take place along title bar + if (e.eventComponent == editorArray[i]) + // || e.eventComponent->getParentComponent() == editorArray[i] || // e.eventComponent->getParentComponent()->getParentComponent() == // editorArray[i]) { + if (e.getNumberOfClicks() == 2) // double-clicks toggle collapse state + { + if (editorArray[i]->getCollapsedState()) + { + editorArray[i]->switchCollapsedState(); + } else { + if (e.y < 22) + { + editorArray[i]->switchCollapsedState(); + } + } + return; + } + + // make sure uncollapsed editors don't accept clicks outside their title bar + if (!editorArray[i]->getCollapsedState() && e.y > 22) + return; + clickInEditor = true; editorArray[i]->select(); @@ -1131,9 +1174,12 @@ const String EditorViewport::saveState(File fileToUse) int saveOrder = 0; XmlElement* xml = new XmlElement("SETTINGS"); - + XmlElement* info = xml->createNewChildElement("INFO"); + XmlElement* version = info->createNewChildElement("VERSION"); + version->addTextElement("0.1"); + Time currentTime = Time::getCurrentTime(); XmlElement* date = info->createNewChildElement("DATE"); @@ -1195,7 +1241,7 @@ const String EditorViewport::saveState(File fileToUse) editor = (GenericEditor*) nextProcessor->getEditor(); - if ((nextProcessor->isSplitter() || nextProcessor->isMerger()) + if ((nextProcessor->isSplitter())// || nextProcessor->isMerger()) && nextProcessor->saveOrder < 0) { splitPoints.add(nextProcessor); @@ -1261,6 +1307,7 @@ const String EditorViewport::saveState(File fileToUse) } getControlPanel()->saveStateToXml(xml); // save the control panel settings + getProcessorList()->saveStateToXml(xml); getUIComponent()->saveStateToXml(xml); // save the UI settings if (! xml->writeToFile(currentFile, String::empty)) @@ -1291,7 +1338,7 @@ const String EditorViewport::loadState(File fileToLoad) // { // return "No configuration selected."; // } - + int maxID=100; currentFile = fileToLoad; std::cout << "Loading processor graph." << std::endl; @@ -1308,6 +1355,34 @@ const String EditorViewport::loadState(File fileToLoad) return "Not a valid file."; } + bool olderVersionFound = true; + forEachXmlChildElement(*xml, element) + { + if (element->hasTagName("INFO")) + { + forEachXmlChildElement(*element, element2) + { + if (element2->hasTagName("VERSION")) + { + String S= element2->getAllSubText(); + double version =S.getDoubleValue(); + if (version >= 0.1) + olderVersionFound = false; + } + } + break; + } + } + if (olderVersionFound) + { + bool response = AlertWindow::showOkCancelBox (AlertWindow::NoIcon, + "Old configuration file.", + "File may not load properly since it could lack some fields. Continute?", + "Yes", "No", 0, 0); + if (!response) + return "Failed To Open " + fileToLoad.getFileName(); + + } clearSignalChain(); String description;// = " "; @@ -1328,6 +1403,9 @@ const String EditorViewport::loadState(File fileToLoad) { int insertionPt = processor->getIntAttribute("insertionPoint"); + currentId = processor->getIntAttribute("NodeId"); + + maxID= (maxID > currentId) ? maxID : currentId ; if (insertionPt == 1) { @@ -1348,6 +1426,7 @@ const String EditorViewport::loadState(File fileToLoad) p = (GenericProcessor*) lastEditor->getProcessor(); p->loadOrder = loadOrder; p->parametersAsXml = processor; + //Sets parameters based on XML files setParametersByXML(p, processor); loadOrder++; @@ -1357,6 +1436,8 @@ const String EditorViewport::loadState(File fileToLoad) splitPoints.add(p); } + signalChainManager->updateVisibleEditors(editorArray[0], 0, 0, UPDATE); + } else if (processor->hasTagName("SWITCH")) { @@ -1390,6 +1471,8 @@ const String EditorViewport::loadState(File fileToLoad) } } + signalChainManager->updateVisibleEditors(editorArray[0], 0, 0, UPDATE); + } } @@ -1411,6 +1494,7 @@ const String EditorViewport::loadState(File fileToLoad) getProcessorGraph()->restoreParameters(); getControlPanel()->loadStateFromXml(xml); // save the control panel settings + getProcessorList()->loadStateFromXml(xml); getUIComponent()->loadStateFromXml(xml); // save the UI settings if (editorArray.size() > 0) @@ -1418,10 +1502,16 @@ const String EditorViewport::loadState(File fileToLoad) refreshEditors(); + getProcessorGraph()->restoreParameters(); + + String error = "Opened "; error += currentFile.getFileName(); delete xml; + + currentId=maxID+1; // make sure future processors don't have overlapping id numbers + return error; } /* Set parameters based on XML.*/ diff --git a/Source/UI/EditorViewport.h b/Source/UI/EditorViewport.h index c47d94395d0582fed8052f31877bd53f03b53811..242befc7d567b5f9ddfde92e83677cdfe7c5ed42 100755 --- a/Source/UI/EditorViewport.h +++ b/Source/UI/EditorViewport.h @@ -210,6 +210,9 @@ private: void resized(); + int currentId; + int maxId; + JUCE_DECLARE_NON_COPYABLE_WITH_LEAK_DETECTOR(EditorViewport); }; @@ -247,7 +250,7 @@ public: /** Returns the editor associated with this SignalChainTabButton.*/ GenericEditor* getEditor() { - return firstEditor; + return firstEditor; } /** Sets the number of this SignalChainTabButton.*/ diff --git a/Source/UI/ProcessorList.cpp b/Source/UI/ProcessorList.cpp index e3c9dd9c8727d13a75efcf4d97a064459a2a119d..c60b9f319e24ee04d104b544e945d7a04b58be79 100755 --- a/Source/UI/ProcessorList.cpp +++ b/Source/UI/ProcessorList.cpp @@ -56,22 +56,26 @@ ProcessorList::ProcessorList() //sources->addSubItem(new ProcessorListItem("Custom FPGA")); sources->addSubItem(new ProcessorListItem("Rhythm FPGA")); sources->addSubItem(new ProcessorListItem("File Reader")); + //sources->addSubItem(new ProcessorListItem("Network Events")); sources->addSubItem(new ProcessorListItem("Serial Port")); //sources->addSubItem(new ProcessorListItem("Event Generator")); ProcessorListItem* filters = new ProcessorListItem("Filters"); filters->addSubItem(new ProcessorListItem("Bandpass Filter")); - //filters->addSubItem(new ProcessorListItem("Event Detector")); filters->addSubItem(new ProcessorListItem("Spike Detector")); //filters->addSubItem(new ProcessorListItem("Resampler")); filters->addSubItem(new ProcessorListItem("Phase Detector")); //filters->addSubItem(new ProcessorListItem("Digital Ref")); filters->addSubItem(new ProcessorListItem("Channel Map")); + //filters->addSubItem(new ProcessorListItem("Eye Tracking")); + ProcessorListItem* sinks = new ProcessorListItem("Sinks"); sinks->addSubItem(new ProcessorListItem("LFP Viewer")); //sinks->addSubItem(new ProcessorListItem("LFP Trig. Avg.")); sinks->addSubItem(new ProcessorListItem("Spike Viewer")); + //sinks->addSubItem(new ProcessorListItem("PSTH")); + //sinks->addSubItem(new ProcessorListItem("Network Sink")); //sinks->addSubItem(new ProcessorListItem("WiFi Output")); //sinks->addSubItem(new ProcessorListItem("Arduino Output")); // sinks->addSubItem(new ProcessorListItem("FPGA Output")); @@ -81,6 +85,7 @@ ProcessorList::ProcessorList() utilities->addSubItem(new ProcessorListItem("Splitter")); utilities->addSubItem(new ProcessorListItem("Merger")); utilities->addSubItem(new ProcessorListItem("Record Control")); + //utilities->addSubItem(new ProcessorListItem("Advancers")); baseItem = new ProcessorListItem("Processors"); baseItem->addSubItem(sources); @@ -113,12 +118,14 @@ ProcessorList::~ProcessorList() } + + bool ProcessorList::isOpen() { return baseItem->isOpen(); } -void ProcessorList::paintCanvas(Graphics& g) +void ProcessorList::paint(Graphics& g) { drawItems(g); @@ -269,7 +276,7 @@ void ProcessorList::clearSelectionState() ProcessorListItem* ProcessorList::getListItemForYPos(int y) { - int bottom = (yBuffer + itemHeight) - getScrollAmount(); + int bottom = (yBuffer + itemHeight); // - getScrollAmount(); //std::cout << "Bottom: " << bottom << std::endl; //std::cout << "Y coordinate: " << y << std::endl; @@ -350,7 +357,7 @@ void ProcessorList::toggleState() repaint(); } -void ProcessorList::mouseDownInCanvas(const MouseEvent& e) +void ProcessorList::mouseDown(const MouseEvent& e) { isDragging = false; @@ -361,15 +368,15 @@ void ProcessorList::mouseDownInCanvas(const MouseEvent& e) //std::cout << xcoord << " " << ycoord << std::endl; - ProcessorListItem* fli = getListItemForYPos(ycoord); + ProcessorListItem* listItem = getListItemForYPos(ycoord); - if (fli != 0) + if (listItem != 0) { //std::cout << "Selecting: " << fli->getName() << std::endl; - if (!fli->hasSubItems()) + if (!listItem->hasSubItems()) { clearSelectionState(); - fli->setSelected(true); + listItem->setSelected(true); } } @@ -378,26 +385,26 @@ void ProcessorList::mouseDownInCanvas(const MouseEvent& e) //std::cout << "No selection." << std::endl; } - if (fli != 0) + if (listItem != 0) { - if (xcoord < getWidth() - getScrollBarWidth()) + if (xcoord < getWidth()) { if (e.mods.isRightButtonDown() || e.mods.isCtrlDown()) { - if (fli->getName().equalsIgnoreCase("Sources")) + if (listItem->getName().equalsIgnoreCase("Sources")) { currentColor = SOURCE_COLOR; } - else if (fli->getName().equalsIgnoreCase("Filters")) + else if (listItem->getName().equalsIgnoreCase("Filters")) { currentColor = FILTER_COLOR; } - else if (fli->getName().equalsIgnoreCase("Utilities")) + else if (listItem->getName().equalsIgnoreCase("Utilities")) { currentColor = UTILITY_COLOR; } - else if (fli->getName().equalsIgnoreCase("Sinks")) + else if (listItem->getName().equalsIgnoreCase("Sinks")) { currentColor = SINK_COLOR; } @@ -420,7 +427,7 @@ void ProcessorList::mouseDownInCanvas(const MouseEvent& e) colourSelector.setColour(ColourSelector::backgroundColourId, Colours::transparentBlack); colourSelector.setSize(300, 275); - Rectangle<int> rect = Rectangle<int>(0,0,10,10); + juce::Rectangle<int> rect = juce::Rectangle<int>(0,0,10,10); CallOutBox callOut(colourSelector, rect, nullptr); callOut.setTopLeftPosition(e.getScreenX(), e.getScreenY()); @@ -431,13 +438,13 @@ void ProcessorList::mouseDownInCanvas(const MouseEvent& e) } else { - fli->reverseOpenState(); + listItem->reverseOpenState(); } } - if (fli == baseItem) + if (listItem == baseItem) { - if (fli->isOpen()) + if (listItem->isOpen()) { getUIComponent()->childComponentChanged(); } @@ -463,24 +470,24 @@ void ProcessorList::changeListenerCallback(ChangeBroadcaster* source) } -void ProcessorList::mouseDragInCanvas(const MouseEvent& e) +void ProcessorList::mouseDrag(const MouseEvent& e) { - if (e.getMouseDownX() < getWidth()-getScrollBarWidth() && !(isDragging)) + if (e.getMouseDownX() < getWidth() && !(isDragging)) { - ProcessorListItem* fli = getListItemForYPos(e.getMouseDownY()); + ProcessorListItem* listItem = getListItemForYPos(e.getMouseDownY()); - if (fli != 0) + if (listItem != 0) { - if (!fli->hasSubItems()) + if (!listItem->hasSubItems()) { isDragging = true; - String b = fli->getParentName(); + String b = listItem->getParentName(); b += "/"; - b += fli->getName(); + b += listItem->getName(); const String dragDescription = b; @@ -498,11 +505,11 @@ void ProcessorList::mouseDragInCanvas(const MouseEvent& e) Image dragImage(Image::ARGB, 100, 15, true); Graphics g(dragImage); - g.setColour(findColour(fli->colorId)); + g.setColour(findColour(listItem->colorId)); g.fillAll(); g.setColour(Colours::white); g.setFont(14); - g.drawSingleLineText(fli->getName(),10,12);//,75,15,Justification::centredRight,true); + g.drawSingleLineText(listItem->getName(),10,12);//,75,15,Justification::centredRight,true); dragImage.multiplyAllAlphas(0.6f); @@ -517,6 +524,113 @@ void ProcessorList::mouseDragInCanvas(const MouseEvent& e) } +void ProcessorList::saveStateToXml(XmlElement* xml) +{ + XmlElement* processorListState = xml->createNewChildElement("PROCESSORLIST"); + + for (int i = 0; i < 5; i++) + { + XmlElement* colorState = processorListState->createNewChildElement("COLOR"); + + int id; + + switch (i) + { + case 0: + id = PROCESSOR_COLOR; + break; + case 1: + id = SOURCE_COLOR; + break; + case 2: + id = FILTER_COLOR; + break; + case 3: + id = SINK_COLOR; + break; + case 4: + id = UTILITY_COLOR; + break; + default: + // do nothing + ; + } + + Colour c = findColour(id); + + colorState->setAttribute("ID", (int) id); + colorState->setAttribute("R", (int) c.getRed()); + colorState->setAttribute("G", (int) c.getGreen()); + colorState->setAttribute("B", (int) c.getBlue()); + + } +} + +void ProcessorList::loadStateFromXml(XmlElement* xml) +{ + forEachXmlChildElement(*xml, xmlNode) + { + if (xmlNode->hasTagName("PROCESSORLIST")) + { + forEachXmlChildElement(*xmlNode, colorNode) + { + setColour(colorNode->getIntAttribute("ID"), + Colour( + colorNode->getIntAttribute("R"), + colorNode->getIntAttribute("G"), + colorNode->getIntAttribute("B"))); + } + } + } + + repaint(); + + getProcessorGraph()->refreshColors(); +} + +Array<Colour> ProcessorList::getColours() +{ + Array<Colour> c; + + c.add(findColour(PROCESSOR_COLOR)); + c.add(findColour(SOURCE_COLOR)); + c.add(findColour(FILTER_COLOR)); + c.add(findColour(SINK_COLOR)); + c.add(findColour(UTILITY_COLOR)); + return c; +} + +void ProcessorList::setColours(Array<Colour> c) +{ + for (int i = 0; i < c.size(); i++) + { + switch (i) + { + case 0: + setColour(PROCESSOR_COLOR, c[i]); + break; + case 1: + setColour(SOURCE_COLOR, c[i]); + break; + case 2: + setColour(FILTER_COLOR, c[i]); + break; + case 3: + setColour(SINK_COLOR, c[i]); + break; + case 4: + setColour(UTILITY_COLOR, c[i]); + break; + default: + ;// do nothing + } + } + + +} + +// =================================================================== + ProcessorListItem::ProcessorListItem(const String& name_) : selected(false), open(true), name(name_) { @@ -609,6 +723,7 @@ void ProcessorListItem::setParentName(const String& name) } } + // Blue slate: // if (parentName.equalsIgnoreCase("Processors")) // { diff --git a/Source/UI/ProcessorList.h b/Source/UI/ProcessorList.h index c19f47f36c183a26554ad135a83821f98732ee49..9873a0eb8dd43a1fcb9694ae4ba72bda6c142e3d 100755 --- a/Source/UI/ProcessorList.h +++ b/Source/UI/ProcessorList.h @@ -25,7 +25,6 @@ #define __PROCESSORLIST_H_C3A661E9__ #include "../../JuceLibraryCode/JuceHeader.h" -#include "../Processors/Visualization/OpenGLCanvas.h" #include "../AccessClass.h" class ProcessorListItem; @@ -48,7 +47,7 @@ class UIComponent; */ -class ProcessorList : public OpenGLCanvas, +class ProcessorList : public Component, public DragAndDropContainer, public AccessClass, public ChangeListener @@ -68,10 +67,22 @@ public: /** Returns the open/closed state of the ProcessorList.*/ bool isOpen(); -private: + /** Draws the ProcessorList. */ + void paint(Graphics& g); + + /** Gets the colors of the different types of processors.*/ + Array<Colour> getColours(); + + /** Sets the colors of the different types of processors.*/ + void setColours(Array<Colour>); - /** Renders the canvas. */ - void paintCanvas(Graphics& g); + /** Saves the ProcessorList state. */ + void saveStateToXml(XmlElement*); + + /** Loads the ProcessorList state. */ + void loadStateFromXml(XmlElement*); + +private: /** The main method for drawing the ProcessorList.*/ void drawItems(Graphics& g); @@ -88,13 +99,13 @@ private: /** Returns the ProcessorListItem that sits at a given y coordinate.*/ ProcessorListItem* getListItemForYPos(int y); - /** Sets the appropriate OpenGL viewport for drawing.*/ + /** Sets the appropriate viewport for drawing.*/ void setViewport(Graphics& g, bool); int currentColor; /** Returns the height requested by the ProcessorList. Determines whether or not - the OpenGLCanvas needs to draw scroll bars.*/ + to draw scroll bars.*/ int getTotalHeight(); /** Deselects all items within the ProcessorList.*/ @@ -107,10 +118,10 @@ private: String category; /** Called when a mouse click begins within the boundaries of the ProcessorList.*/ - void mouseDownInCanvas(const MouseEvent& e); + void mouseDown(const MouseEvent& e); /** Called when a mouse drag occurs within the boundaries of the ProcessorList.*/ - void mouseDragInCanvas(const MouseEvent& e); + void mouseDrag(const MouseEvent& e); /** The base item in the list.*/ ScopedPointer<ProcessorListItem> baseItem; diff --git a/Source/UI/SignalChainManager.cpp b/Source/UI/SignalChainManager.cpp index e4d9d063b8ca38f03d438e150b632e8b43a03eba..6f2af4e25dde3df75db89d629a866dc4e3b5d4ab 100755 --- a/Source/UI/SignalChainManager.cpp +++ b/Source/UI/SignalChainManager.cpp @@ -187,25 +187,38 @@ void SignalChainManager::updateVisibleEditors(GenericEditor* activeEditor, std::cout << " Removing editor." << std::endl; GenericProcessor* p = (GenericProcessor*) editorArray[index]->getProcessor(); + + // GenericProcessor* source = p->getSourceNode(); + if (p->getSourceNode() != nullptr) + if (p->getSourceNode()->isSplitter()) + p->getSourceNode()->setSplitterDestNode(nullptr); // if the processor to be removed is a merger, // we need to inform the other source that its merger has disappeared if (p->isMerger()) { p->switchIO(); - if (p->getSourceNode() != 0) - p->getSourceNode()->setDestNode(0); + if (p->getSourceNode() != nullptr) + p->getSourceNode()->setDestNode(nullptr); } // if the processor to be removed is a splitter, we need to make sure // there aren't any orphaned processors if (p->isSplitter()) { - p->switchIO(); - if (p->getDestNode() != 0) + p->switchIO(0); + if (p->getDestNode() != nullptr) { std::cout << "Found an orphaned signal chain" << std::endl; - p->getDestNode()->setSourceNode(0); + p->getDestNode()->setSourceNode(nullptr); + createNewTab(p->getDestNode()->getEditor()); + } + + p->switchIO(1); + if (p->getDestNode() != nullptr) + { + std::cout << "Found an orphaned signal chain" << std::endl; + p->getDestNode()->setSourceNode(nullptr); createNewTab(p->getDestNode()->getEditor()); } } @@ -220,12 +233,17 @@ void SignalChainManager::updateVisibleEditors(GenericEditor* activeEditor, if (editorArray.size() > 0) { - GenericProcessor* p = (GenericProcessor*) editorArray[0]->getProcessor(); - merger = (p->isMerger() && p->stillHasSource()); + // take the next processor in the array + GenericProcessor* p2 = (GenericProcessor*) editorArray[0]->getProcessor(); + merger = (p2->isMerger() && p2->stillHasSource()); if (merger) { std::cout << "We've got a merger!" << std::endl; - //p->switchSource(); + //p2->switchIO(0); + p2->setMergerSourceNode(p->getSourceNode()); + MergerEditor* me = (MergerEditor*) editorArray[0]; + me->switchSource(); + // p2->setMergerSourceNode(nullptr); } } @@ -358,22 +376,21 @@ void SignalChainManager::updateVisibleEditors(GenericEditor* activeEditor, GenericProcessor* currentProcessor = (GenericProcessor*) editorToAdd->getProcessor(); GenericProcessor* source = currentProcessor->getSourceNode(); - if (source != 0) + if (source != nullptr) { std::cout << "Source: " << source->getName() << std::endl; // need to switch the splitter somehow - // if (action == ACTIVATE || action == UPDATE) - // { - // if (source->isSplitter()) - // { - // source->setPathToProcessor(currentProcessor); - // } - // } + if (action == ACTIVATE || action == UPDATE) + { + if (source->isSplitter()) + { + source->setPathToProcessor(currentProcessor); + } + } editorToAdd = (GenericEditor*) source->getEditor(); - } else { @@ -406,8 +423,10 @@ void SignalChainManager::updateVisibleEditors(GenericEditor* activeEditor, { std::cout << "It's a merger!" << std::endl; + editorToAdd->switchIO(0); + if (dest->getSourceNode() != currentProcessor) - editorToAdd->switchSource(); + editorToAdd->switchIO(1); } @@ -499,25 +518,27 @@ void SignalChainManager::updateVisibleEditors(GenericEditor* activeEditor, GenericEditor* source = signalChainArray[n]->getEditor(); GenericProcessor* p = source->getProcessor(); - p->update(); - - if (p->isSplitter()) - { - splitters.add(p); - } + // p->update(); - GenericProcessor* dest = p->getDestNode(); + // GenericProcessor* dest = p->getDestNode(); - while (dest != 0) + while (p != 0) { // iterate through processors - dest->update(); - dest = dest->getDestNode(); + p->update(); + + if (p->isSplitter()) + { + splitters.add(p); + } + + p = p->getDestNode(); - if (dest == 0 && splitters.size() > 0) + if (p == 0 && splitters.size() > 0) { - splitters.getFirst()->switchIO(); - dest = splitters[0]->getDestNode(); + splitters.getFirst()->switchIO(); // switch the signal chain + p = splitters[0]->getDestNode(); + splitters.getFirst()->switchIO(); // switch it back splitters.remove(0); } }