uint32 PMixDocument::addNode (const PluginDescription* desc, double x, double y) { AudioProcessorGraph::Node* node = nullptr; if (desc != nullptr) { String errorMessage; AudioPluginInstance* instance = audioEngine.createPluginInstance(*desc, errorMessage); jassert(instance != nullptr); node = audioEngine.getGraph().addNode (instance); FaustAudioPluginInstance* faustProc = dynamic_cast<FaustAudioPluginInstance*>(instance); if (faustProc) { faustProc->initialize(getLibraryPath(), drawPath); } if (node != nullptr) { node->properties.set ("x", x); node->properties.set ("y", y); node->properties.set ("uiLastX", Random::getSystemRandom().nextInt (500)); node->properties.set ("uiLastY", Random::getSystemRandom().nextInt (500)); node->properties.set ("uiStatus", kUIStatusEmbed); if (!InternalPluginFormat::isInternalFormat(desc->name)) { node->properties.set ("colour", defaultColours.getNextColour().toString()); node->properties.set ("iposx", x); node->properties.set ("iposy", y); node->properties.set ("update", false); Array<var> presets; node->properties.set("presets", presets); Array<var> params; node->properties.set("params", params); } changed(); } else { AlertWindow::showMessageBox (AlertWindow::WarningIcon, TRANS("Couldn't create node"), errorMessage); return 0xFFFFFFFF; } } return node->nodeID; }
void NodeComponent::update() { const AudioProcessorGraph::Node::Ptr f (audioEngine.getDoc().getNodeForId (nodeID)); if (f == nullptr) { delete this; return; } numIns = f->getProcessor()->getTotalNumInputChannels(); if (f->getProcessor()->acceptsMidi()) ++numIns; numOuts = f->getProcessor()->getTotalNumOutputChannels(); if (f->getProcessor()->producesMidi()) ++numOuts; FaustAudioPluginInstance* faustProc = dynamic_cast<FaustAudioPluginInstance*>(f->getProcessor()); if (faustProc) highlight = faustProc->getHighlight(); int w = 10; int h = 50; // Update width based on number of I/O w = jmax (w, PINS_LEFT_OFFSET + ((jmax (numIns, numOuts) + 1) * OFFSET_BETWEEN_PINS)); String name = f->getProcessor()->getName(); setName (name); if (numIns != numInputs || numOuts != numOutputs || editor == nullptr) { numInputs = numIns; numOutputs = numOuts; deleteAllChildren(); addAndMakeVisible(nodeName = new Label(name, name)); nodeName->setJustificationType(Justification::centred); nodeName->setInterceptsMouseClicks(false, false); nodeName->setFont(font); w = jmax (w, nodeName->getFont().getStringWidth(name) + 15); if(!InternalPluginFormat::isInternalFormat(name) && f->getProcessor()->getNumParameters() > 0) { int uiStatus = f->properties["uiStatus"]; if(uiStatus == kUIStatusEmbed) { addAndMakeVisible(editor = new PMixGenericAudioProcessorEditor (audioEngine, f->getProcessor(), f->nodeID)); w = jmax (w, editor->getWidth() + 20 ); if (editor->getContentHeight() > 300) { editor->setSize(editor->getWidth(), 100); } h += jmin (320, editor->getContentHeight() + 20); } } setSize (w, h); int i; for (i = 0; i < f->getProcessor()->getTotalNumInputChannels(); ++i) addAndMakeVisible (new PinComponent (audioEngine, nodeID, i, true)); if (f->getProcessor()->acceptsMidi()) addAndMakeVisible (new PinComponent (audioEngine, nodeID, PMixDocument::midiChannelNumber, true)); for (i = 0; i < f->getProcessor()->getTotalNumOutputChannels(); ++i) addAndMakeVisible (new PinComponent (audioEngine, nodeID, i, false)); if (f->getProcessor()->producesMidi()) addAndMakeVisible (new PinComponent (audioEngine, nodeID, PMixDocument::midiChannelNumber, false)); resized(); } { double x, y; audioEngine.getDoc().getNodePosition (nodeID, x, y); setCentreRelative ((float) x, (float) y); } if(faustProc != nullptr) { if(faustProc->getCompilerMessage() != String::empty) bubbleMessage(faustProc->getCompilerMessage()); } }
void PMixDocument::createNodeFromXml (XmlElement& xml, const String& newSourceCode) { PluginDescription pd; forEachXmlChildElement (xml, e) { if (pd.loadFromXml (*e)) break; } String errorMessage; AudioPluginInstance* instance = audioEngine.createPluginInstance(pd, errorMessage); jassert(instance != nullptr); if (pd.pluginFormatName == "FAUST") { FaustAudioPluginInstance* faustProc = dynamic_cast<FaustAudioPluginInstance*>(instance); faustProc->initialize(getLibraryPath(), drawPath); if (newSourceCode.length()) faustProc->setSourceCode(newSourceCode, true); // TODO: this is a bit wrong! faustProc->prepareToPlay(44100., 8192); // xml.setAttribute("numInputs", faustProc->getNumInputChannels()); // xml.setAttribute("numOutputs", faustProc->getNumOutputChannels()); ??? } AudioProcessorGraph::Node::Ptr node (audioEngine.getGraph().addNode (instance, xml.getIntAttribute ("uid"))); if (!newSourceCode.length()) { if (const XmlElement* const state = xml.getChildByName ("STATE")) { MemoryBlock m; m.fromBase64Encoding (state->getAllSubText()); node->getProcessor()->setStateInformation (m.getData(), (int) m.getSize()); } } node->properties.set ("x", xml.getDoubleAttribute ("x")); node->properties.set ("y", xml.getDoubleAttribute ("y")); node->properties.set ("uiLastX", xml.getIntAttribute ("uiLastX")); node->properties.set ("uiLastY", xml.getIntAttribute ("uiLastY")); node->properties.set ("uiStatus", xml.getIntAttribute ("uiStatus")); // presets etc for faust & plugin nodes if(!InternalPluginFormat::isInternalFormat(pd.name)) { node->properties.set ("colour", xml.getStringAttribute ("colour")); node->properties.set ("iposx", xml.getDoubleAttribute ("iposx")); node->properties.set ("iposy", xml.getDoubleAttribute ("iposy")); if (const XmlElement* const params = xml.getChildByName ("PARAMS")) { var vparams = JSON::parse(params->getAllSubText()); node->properties.set ("params", vparams); } Array<var> presetsArr; forEachXmlChildElement (xml, e) { if (e->hasTagName ("PRESET")) { DynamicObject* obj = new DynamicObject(); obj->setProperty("name", e->getStringAttribute("name")); obj->setProperty("x", e->getDoubleAttribute("x")); obj->setProperty("y", e->getDoubleAttribute("y")); obj->setProperty("radius", e->getDoubleAttribute("radius")); obj->setProperty("hidden", e->getBoolAttribute("hidden")); // obj->setProperty("distance", e->getDoubleAttribute("distance")); obj->setProperty("coeff", e->getDoubleAttribute("coeff")); var vparams = JSON::parse(e->getAllSubText()); obj->setProperty("state", vparams); obj->setProperty("uid", e->getIntAttribute("uid")); var preset = var(obj); presetsArr.add(preset); } } node->properties.set("presets", presetsArr); }
void WebBrowser::changeListenerCallback (ChangeBroadcaster* source) { PMixDocument* doc = dynamic_cast<PMixDocument*>(source); // every time the doc changes, loop over nodes and register as a listener to all the faust nodes. if (doc) { for (int i = 0; i <audioEngine.getGraph().getNumNodes(); i++) { FaustAudioPluginInstance* faustProc = dynamic_cast<FaustAudioPluginInstance*>(audioEngine.getDoc().getNode(i)->getProcessor()); if (faustProc) faustProc->getFactory()->registerSVGThreadListenser(this); } return; } GraphEditor* pgraphEditor = dynamic_cast<GraphEditor*>(source); if (pgraphEditor) { if(pgraphEditor->getLassoSelection().getNumSelected() == 1) { FilterComponent* selectedItem = dynamic_cast<FilterComponent*>(pgraphEditor->getLassoSelection().getSelectedItem(0)); if (selectedItem) { FaustAudioPluginInstance* faustProc = dynamic_cast<FaustAudioPluginInstance*>(audioEngine.getDoc().getNodeForId(selectedItem->nodeId)->getProcessor()); if (faustProc) { if (!faustProc->getHighlight()) { browser->goToURL(audioEngine.getDoc().getLibraryPath() + "wait.html"); } else browser->goToURL(""); return; } } } } FaustgenFactory::SVGRenderThread* thread = dynamic_cast<FaustgenFactory::SVGRenderThread*>(source); // if an SVGRenderThread has triggered this change message if (thread) { // if a single item is selected in the graph editor update the browser if(graphEditor.getLassoSelection().getNumSelected() == 1) { FilterComponent* selectedItem = dynamic_cast<FilterComponent*>(graphEditor.getLassoSelection().getSelectedItem(0)); if (selectedItem) { browser->goToURL(thread->getFactory()->getHTMLURI()); return; } } } browser->goToURL(""); }