From 8450921d5309c5ba677997e7ca722a466c8dc222 Mon Sep 17 00:00:00 2001 From: David Robillard Date: Sun, 30 Sep 2007 23:36:39 +0000 Subject: Working port notification for LV2 GUIs (ll-plugins VU meter works in Ingen now). git-svn-id: http://svn.drobilla.net/lad/ingen@790 a436a847-0d15-0410-975c-d299462d15a1 --- src/common/interface/EngineInterface.hpp | 4 ++ src/libs/client/OSCEngineSender.cpp | 18 ++++++ src/libs/client/OSCEngineSender.hpp | 4 ++ src/libs/engine/Makefile.am | 8 +-- src/libs/engine/OSCEngineReceiver.cpp | 40 +++++++++++-- src/libs/engine/OSCEngineReceiver.hpp | 2 + src/libs/engine/QueuedEngineInterface.cpp | 18 +++++- src/libs/engine/QueuedEngineInterface.hpp | 4 ++ src/libs/engine/events.hpp | 10 ++-- src/libs/engine/events/DisablePatchEvent.cpp | 70 ---------------------- src/libs/engine/events/DisablePatchEvent.hpp | 53 ---------------- src/libs/engine/events/EnablePatchEvent.cpp | 23 ++++--- src/libs/engine/events/EnablePatchEvent.hpp | 7 ++- .../engine/events/EnablePortBroadcastingEvent.cpp | 29 +++------ .../engine/events/EnablePortBroadcastingEvent.hpp | 4 +- src/libs/engine/events/Makefile.am | 4 +- src/libs/gui/NodeModule.cpp | 36 +++++++++-- src/libs/gui/NodeModule.hpp | 3 + 18 files changed, 162 insertions(+), 175 deletions(-) delete mode 100644 src/libs/engine/events/DisablePatchEvent.cpp delete mode 100644 src/libs/engine/events/DisablePatchEvent.hpp diff --git a/src/common/interface/EngineInterface.hpp b/src/common/interface/EngineInterface.hpp index 8bbd6f18..b3827a74 100644 --- a/src/common/interface/EngineInterface.hpp +++ b/src/common/interface/EngineInterface.hpp @@ -119,6 +119,10 @@ public: uint32_t data_size, const void* data) = 0; + virtual void enable_port_broadcasting(const string& port_path) = 0; + + virtual void disable_port_broadcasting(const string& port_path) = 0; + virtual void set_program(const string& node_path, uint32_t bank, uint32_t program) = 0; diff --git a/src/libs/client/OSCEngineSender.cpp b/src/libs/client/OSCEngineSender.cpp index 1618f2a1..e3183f78 100644 --- a/src/libs/client/OSCEngineSender.cpp +++ b/src/libs/client/OSCEngineSender.cpp @@ -450,6 +450,24 @@ OSCEngineSender::set_port_value_immediate(const string& port_path, } } + +void +OSCEngineSender::enable_port_broadcasting(const string& port_path) +{ + lo_send(_engine_addr, "/ingen/enable_port_broadcasting", "is", + next_id(), + port_path.c_str()); +} + + +void +OSCEngineSender::disable_port_broadcasting(const string& port_path) +{ + lo_send(_engine_addr, "/ingen/disable_port_broadcasting", "is", + next_id(), + port_path.c_str()); +} + void OSCEngineSender::set_program(const string& node_path, diff --git a/src/libs/client/OSCEngineSender.hpp b/src/libs/client/OSCEngineSender.hpp index c91dfbbd..c97c4e94 100644 --- a/src/libs/client/OSCEngineSender.hpp +++ b/src/libs/client/OSCEngineSender.hpp @@ -132,6 +132,10 @@ public: uint32_t voice, uint32_t data_size, const void* data); + + void enable_port_broadcasting(const string& port_path); + + void disable_port_broadcasting(const string& port_path); void set_program(const string& node_path, uint32_t bank, diff --git a/src/libs/engine/Makefile.am b/src/libs/engine/Makefile.am index 5607f3db..9aa8be9a 100644 --- a/src/libs/engine/Makefile.am +++ b/src/libs/engine/Makefile.am @@ -106,6 +106,8 @@ libingen_engine_la_SOURCES = \ events.hpp \ events/AddNodeEvent.cpp \ events/AddNodeEvent.hpp \ + events/AddPortEvent.cpp \ + events/AddPortEvent.hpp \ events/AllNotesOffEvent.cpp \ events/AllNotesOffEvent.hpp \ events/ClearPatchEvent.cpp \ @@ -118,8 +120,6 @@ libingen_engine_la_SOURCES = \ events/DeactivateEvent.hpp \ events/DestroyEvent.cpp \ events/DestroyEvent.hpp \ - events/DisablePatchEvent.cpp \ - events/DisablePatchEvent.hpp \ events/DisconnectNodeEvent.cpp \ events/DisconnectNodeEvent.hpp \ events/DisconnectPortEvent.cpp \ @@ -128,8 +128,8 @@ libingen_engine_la_SOURCES = \ events/DisconnectionEvent.hpp \ events/EnablePatchEvent.cpp \ events/EnablePatchEvent.hpp \ - events/EnablePortMonitoringEvent.cpp \ - events/EnablePortMonitoringEvent.hpp \ + events/EnablePortBroadcastingEvent.cpp \ + events/EnablePortBroadcastingEvent.hpp \ events/LoadPluginsEvent.cpp \ events/LoadPluginsEvent.hpp \ events/MidiLearnEvent.cpp \ diff --git a/src/libs/engine/OSCEngineReceiver.cpp b/src/libs/engine/OSCEngineReceiver.cpp index d2d7a4a0..3fb9e189 100644 --- a/src/libs/engine/OSCEngineReceiver.cpp +++ b/src/libs/engine/OSCEngineReceiver.cpp @@ -63,7 +63,7 @@ OSCEngineReceiver::OSCEngineReceiver(Engine& engine, size_t queue_size, uint16_t } // For debugging, print all incoming OSC messages - lo_server_add_method(_server, NULL, NULL, generic_cb, NULL); + //lo_server_add_method(_server, NULL, NULL, generic_cb, NULL); // Set response address for this message. // It's important this is first and returns nonzero. @@ -98,6 +98,8 @@ OSCEngineReceiver::OSCEngineReceiver(Engine& engine, size_t queue_size, uint16_t lo_server_add_method(_server, "/ingen/disconnect_all", "is", disconnect_all_cb, this); lo_server_add_method(_server, "/ingen/set_port_value", NULL, set_port_value_cb, this); lo_server_add_method(_server, "/ingen/set_port_value_immediate", NULL, set_port_value_immediate_cb, this); + lo_server_add_method(_server, "/ingen/enable_port_broadcasting", NULL, enable_port_broadcasting_cb, this); + lo_server_add_method(_server, "/ingen/disable_port_broadcasting", NULL, disable_port_broadcasting_cb, this); lo_server_add_method(_server, "/ingen/note_on", "isii", note_on_cb, this); lo_server_add_method(_server, "/ingen/note_off", "isi", note_off_cb, this); lo_server_add_method(_server, "/ingen/all_notes_off", "isi", all_notes_off_cb, this); @@ -629,13 +631,13 @@ OSCEngineReceiver::_set_port_value_immediate_cb(const char* path, const char* ty if (argc == 3) { if (types[2] == 'f') { const float value = argv[2]->f; - set_port_value_immediate(port_path, "who cares", sizeof(float), &value); + set_port_value_immediate(port_path, "", sizeof(float), &value); return 0; } else if (types[2] == 'b') { lo_blob b = argv[2]; size_t data_size = lo_blob_datasize(b); void* data = lo_blob_dataptr(b); - set_port_value_immediate(port_path, "who cares", data_size, data); + set_port_value_immediate(port_path, "", data_size, data); return 0; } else { return 1; @@ -643,13 +645,13 @@ OSCEngineReceiver::_set_port_value_immediate_cb(const char* path, const char* ty } else { if (types[3] == 'f') { const float value = argv[3]->f; - set_port_value_immediate(port_path, "who cares", argv[2]->i, sizeof(float), &value); + set_port_value_immediate(port_path, "", argv[2]->i, sizeof(float), &value); return 0; } else if (types[3] == 'b') { lo_blob b = argv[3]; size_t data_size = lo_blob_datasize(b); void* data = lo_blob_dataptr(b); - set_port_value_immediate(port_path, "who cares", argv[2]->i, data_size, data); + set_port_value_immediate(port_path, "", argv[2]->i, data_size, data); return 0; } else { return 1; @@ -730,6 +732,34 @@ OSCEngineReceiver::_set_port_value_cb(const char* path, const char* types, lo_ar } +/** \page engine_osc_namespace + *

\b /ingen/enable_port_broadcasting - Enable broadcasting of changing port values + * \arg \b response-id (integer) + * \arg \b port-path (string) - Name of port

\n \n + */ +int +OSCEngineReceiver::_enable_port_broadcasting_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) +{ + const char* port_path = &argv[1]->s; + enable_port_broadcasting(port_path); + return 0; +} + + +/** \page engine_osc_namespace + *

\b /ingen/disable_port_broadcasting - Enable broadcasting of changing port values + * \arg \b response-id (integer) + * \arg \b port-path (string) - Name of port

\n \n + */ +int +OSCEngineReceiver::_disable_port_broadcasting_cb(const char* path, const char* types, lo_arg** argv, int argc, lo_message msg) +{ + const char* port_path = &argv[1]->s; + disable_port_broadcasting(port_path); + return 0; +} + + /** \page engine_osc_namespace *

\b /ingen/note_on - Triggers a note-on, just as if it came from MIDI * \arg \b response-id (integer) diff --git a/src/libs/engine/OSCEngineReceiver.hpp b/src/libs/engine/OSCEngineReceiver.hpp index 75cbda7c..d46bc7c3 100644 --- a/src/libs/engine/OSCEngineReceiver.hpp +++ b/src/libs/engine/OSCEngineReceiver.hpp @@ -100,6 +100,8 @@ private: LO_HANDLER(disconnect_all); LO_HANDLER(set_port_value); LO_HANDLER(set_port_value_immediate); + LO_HANDLER(enable_port_broadcasting); + LO_HANDLER(disable_port_broadcasting); LO_HANDLER(note_on); LO_HANDLER(note_off); LO_HANDLER(all_notes_off); diff --git a/src/libs/engine/QueuedEngineInterface.cpp b/src/libs/engine/QueuedEngineInterface.cpp index 72be00aa..4e138c57 100644 --- a/src/libs/engine/QueuedEngineInterface.cpp +++ b/src/libs/engine/QueuedEngineInterface.cpp @@ -196,14 +196,14 @@ QueuedEngineInterface::set_polyphonic(const string& path, bool poly) void QueuedEngineInterface::enable_patch(const string& patch_path) { - push_queued(new EnablePatchEvent(_engine, _responder, now(), patch_path)); + push_queued(new EnablePatchEvent(_engine, _responder, now(), patch_path, true)); } void QueuedEngineInterface::disable_patch(const string& patch_path) { - push_queued(new DisablePatchEvent(_engine, _responder, now(), patch_path)); + push_queued(new EnablePatchEvent(_engine, _responder, now(), patch_path, false)); } @@ -273,6 +273,20 @@ QueuedEngineInterface::set_port_value_immediate(const string& port_path, } +void +QueuedEngineInterface::enable_port_broadcasting(const string& port_path) +{ + push_queued(new EnablePortBroadcastingEvent(_engine, _responder, now(), port_path, true)); +} + + +void +QueuedEngineInterface::disable_port_broadcasting(const string& port_path) +{ + push_queued(new EnablePortBroadcastingEvent(_engine, _responder, now(), port_path, false)); +} + + void QueuedEngineInterface::set_program(const string& node_path, uint32_t bank, diff --git a/src/libs/engine/QueuedEngineInterface.hpp b/src/libs/engine/QueuedEngineInterface.hpp index 3a0ad016..c860c0f8 100644 --- a/src/libs/engine/QueuedEngineInterface.hpp +++ b/src/libs/engine/QueuedEngineInterface.hpp @@ -139,6 +139,10 @@ public: uint32_t voice, uint32_t data_size, const void* data); + + virtual void enable_port_broadcasting(const string& port_path); + + virtual void disable_port_broadcasting(const string& port_path); virtual void set_program(const string& node_path, uint32_t bank, diff --git a/src/libs/engine/events.hpp b/src/libs/engine/events.hpp index 2660c6c1..82c948b2 100644 --- a/src/libs/engine/events.hpp +++ b/src/libs/engine/events.hpp @@ -28,10 +28,10 @@ #include "CreatePatchEvent.hpp" #include "DeactivateEvent.hpp" #include "DestroyEvent.hpp" -#include "DisablePatchEvent.hpp" -#include "DisconnectionEvent.hpp" #include "DisconnectNodeEvent.hpp" +#include "DisconnectionEvent.hpp" #include "EnablePatchEvent.hpp" +#include "EnablePortBroadcastingEvent.hpp" #include "LoadPluginsEvent.hpp" #include "MidiLearnEvent.hpp" #include "NoteOffEvent.hpp" @@ -46,17 +46,17 @@ #include "RequestPluginsEvent.hpp" #include "RequestPortValueEvent.hpp" #include "SetMetadataEvent.hpp" -#include "SetPolyphonyEvent.hpp" #include "SetPolyphonicEvent.hpp" +#include "SetPolyphonyEvent.hpp" #include "SetPortValueEvent.hpp" #include "SetPortValueQueuedEvent.hpp" #include "UnregisterClientEvent.hpp" #ifdef HAVE_DSSI -#include "DSSIUpdateEvent.hpp" -#include "DSSIControlEvent.hpp" #include "DSSIConfigureEvent.hpp" +#include "DSSIControlEvent.hpp" #include "DSSIProgramEvent.hpp" +#include "DSSIUpdateEvent.hpp" #endif #endif // EVENTS_H diff --git a/src/libs/engine/events/DisablePatchEvent.cpp b/src/libs/engine/events/DisablePatchEvent.cpp deleted file mode 100644 index bc5219a6..00000000 --- a/src/libs/engine/events/DisablePatchEvent.cpp +++ /dev/null @@ -1,70 +0,0 @@ -/* This file is part of Ingen. - * Copyright (C) 2007 Dave Robillard - * - * Ingen is free software; you can redistribute it and/or modify it under the - * terms of the GNU General Public License as published by the Free Software - * Foundation; either version 2 of the License, or (at your option) any later - * version. - * - * Ingen is distributed in the hope that it will be useful, but WITHOUT ANY - * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS - * FOR A PARTICULAR PURPOSE. See the GNU General Public License for details. - * - * You should have received a copy of the GNU General Public License along - * with this program; if not, write to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#include "DisablePatchEvent.hpp" -#include "Responder.hpp" -#include "Engine.hpp" -#include "Patch.hpp" -#include "ClientBroadcaster.hpp" -#include "util.hpp" -#include "ObjectStore.hpp" -#include "Port.hpp" - -namespace Ingen { - - -DisablePatchEvent::DisablePatchEvent(Engine& engine, SharedPtr responder, SampleCount timestamp, const string& patch_path) -: QueuedEvent(engine, responder, timestamp), - _patch_path(patch_path), - _patch(NULL) -{ -} - - -void -DisablePatchEvent::pre_process() -{ - _patch = _engine.object_store()->find_patch(_patch_path); - - QueuedEvent::pre_process(); -} - - -void -DisablePatchEvent::execute(ProcessContext& context) -{ - QueuedEvent::execute(context); - - if (_patch != NULL) - _patch->disable(); -} - - -void -DisablePatchEvent::post_process() -{ - if (_patch != NULL) { - _responder->respond_ok(); - _engine.broadcaster()->send_patch_disable(_patch_path); - } else { - _responder->respond_error(string("Patch ") + _patch_path + " not found"); - } -} - - -} // namespace Ingen - diff --git a/src/libs/engine/events/DisablePatchEvent.hpp b/src/libs/engine/events/DisablePatchEvent.hpp deleted file mode 100644 index 1a208246..00000000 --- a/src/libs/engine/events/DisablePatchEvent.hpp +++ /dev/null @@ -1,53 +0,0 @@ -/* This file is part of Ingen. - * Copyright (C) 2007 Dave Robillard - * - * Ingen is free software; you can redistribute it and/or modify it under the - * terms of the GNU General Public License as published by the Free Software - * Foundation; either version 2 of the License, or (at your option) any later - * version. - * - * Ingen is distributed in the hope that it will be useful, but WITHOUT ANY - * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS - * FOR A PARTICULAR PURPOSE. See the GNU General Public License for details. - * - * You should have received a copy of the GNU General Public License along - * with this program; if not, write to the Free Software Foundation, Inc., - * 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA - */ - -#ifndef DISABLEPATCHEVENT_H -#define DISABLEPATCHEVENT_H - -#include -#include "QueuedEvent.hpp" - -using std::string; - -namespace Ingen { - -class Patch; - - -/** Disables a Patch's DSP processing. - * - * \ingroup engine - */ -class DisablePatchEvent : public QueuedEvent -{ -public: - DisablePatchEvent(Engine& engine, SharedPtr responder, SampleCount timestamp, const string& patch_path); - - void pre_process(); - void execute(ProcessContext& context); - void post_process(); - -private: - string _patch_path; - Patch* _patch; -}; - - -} // namespace Ingen - - -#endif // DISABLEPATCHEVENT_H diff --git a/src/libs/engine/events/EnablePatchEvent.cpp b/src/libs/engine/events/EnablePatchEvent.cpp index d0d872bb..e380340f 100644 --- a/src/libs/engine/events/EnablePatchEvent.cpp +++ b/src/libs/engine/events/EnablePatchEvent.cpp @@ -26,11 +26,12 @@ namespace Ingen { -EnablePatchEvent::EnablePatchEvent(Engine& engine, SharedPtr responder, SampleCount timestamp, const string& patch_path) +EnablePatchEvent::EnablePatchEvent(Engine& engine, SharedPtr responder, SampleCount timestamp, const string& patch_path, bool enable) : QueuedEvent(engine, responder, timestamp), _patch_path(patch_path), _patch(NULL), - _compiled_patch(NULL) + _compiled_patch(NULL), + _enable(enable) { } @@ -40,10 +41,10 @@ EnablePatchEvent::pre_process() { _patch = _engine.object_store()->find_patch(_patch_path); - if (_patch != NULL) { + if (_enable && _patch) { /* Any event that requires a new process order will set the patch's - * process order to NULL if it is executed when the patch is not - * active. So, if the PO is NULL, calculate it here */ + * compiled_patch to NULL if it is executed when the patch is not + * active. So, if the CP is NULL, calculate it here */ if (_patch->compiled_patch() == NULL) _compiled_patch = _patch->compile(); } @@ -58,9 +59,12 @@ EnablePatchEvent::execute(ProcessContext& context) QueuedEvent::execute(context); if (_patch != NULL) { - _patch->enable(); + if (_enable) + _patch->enable(); + else + _patch->disable(); - if (_patch->compiled_patch() == NULL) + if (_enable && _patch->compiled_patch() == NULL) _patch->compiled_patch(_compiled_patch); } } @@ -71,7 +75,10 @@ EnablePatchEvent::post_process() { if (_patch != NULL) { _responder->respond_ok(); - _engine.broadcaster()->send_patch_enable(_patch_path); + if (_enable) + _engine.broadcaster()->send_patch_enable(_patch_path); + else + _engine.broadcaster()->send_patch_disable(_patch_path); } else { _responder->respond_error(string("Patch ") + _patch_path + " not found"); } diff --git a/src/libs/engine/events/EnablePatchEvent.hpp b/src/libs/engine/events/EnablePatchEvent.hpp index f0ba5714..a5d7d7e7 100644 --- a/src/libs/engine/events/EnablePatchEvent.hpp +++ b/src/libs/engine/events/EnablePatchEvent.hpp @@ -39,7 +39,11 @@ class CompiledPatch; class EnablePatchEvent : public QueuedEvent { public: - EnablePatchEvent(Engine& engine, SharedPtr responder, SampleCount timestamp, const string& patch_path); + EnablePatchEvent(Engine& engine, + SharedPtr responder, + SampleCount timestamp, + const string& patch_path, + bool enable); void pre_process(); void execute(ProcessContext& context); @@ -49,6 +53,7 @@ private: string _patch_path; Patch* _patch; CompiledPatch* _compiled_patch; // Patch's new process order + bool _enable; }; diff --git a/src/libs/engine/events/EnablePortBroadcastingEvent.cpp b/src/libs/engine/events/EnablePortBroadcastingEvent.cpp index e432a884..27603e86 100644 --- a/src/libs/engine/events/EnablePortBroadcastingEvent.cpp +++ b/src/libs/engine/events/EnablePortBroadcastingEvent.cpp @@ -33,10 +33,12 @@ namespace Ingen { EnablePortBroadcastingEvent::EnablePortBroadcastingEvent(Engine& engine, SharedPtr responder, SampleCount timestamp, - const std::string& port_path) + const std::string& port_path, + bool enable) : QueuedEvent(engine, responder, timestamp), _port_path(port_path), - _port(NULL) + _port(NULL), + _enable(enable) { } @@ -55,31 +57,18 @@ EnablePortBroadcastingEvent::execute(ProcessContext& context) { QueuedEvent::execute(context); -#if 0 - assert(_time >= start && _time <= end); - - if (_port != NULL && _port->type() == DataType::FLOAT) - _value = ((AudioBuffer*)_port->buffer(0))->value_at(0/*_time - start*/); - else - _port = NULL; // triggers error response -#endif + if (_port) + _port->monitor(_enable); } void EnablePortBroadcastingEvent::post_process() { -#if 0 - string msg; - if (!_port) { - _responder->respond_error("Unable to find port for get_value responder."); - } else if (_responder->client()) { + if (_port) _responder->respond_ok(); - _responder->client()->control_change(_port_path, _value); - } else { - _responder->respond_error("Unable to find client to send port value"); - } -#endif + else + _responder->respond_error("Unable to find port for get_value responder."); } diff --git a/src/libs/engine/events/EnablePortBroadcastingEvent.hpp b/src/libs/engine/events/EnablePortBroadcastingEvent.hpp index 55f7decb..e24389cb 100644 --- a/src/libs/engine/events/EnablePortBroadcastingEvent.hpp +++ b/src/libs/engine/events/EnablePortBroadcastingEvent.hpp @@ -41,7 +41,8 @@ public: EnablePortBroadcastingEvent(Engine& engine, SharedPtr responder, SampleCount timestamp, - const std::string& port_path); + const std::string& port_path, + bool enable); void pre_process(); void execute(ProcessContext& context); @@ -50,6 +51,7 @@ public: private: const std::string _port_path; Port* _port; + bool _enable; }; diff --git a/src/libs/engine/events/Makefile.am b/src/libs/engine/events/Makefile.am index e634b63b..7d51ce90 100644 --- a/src/libs/engine/events/Makefile.am +++ b/src/libs/engine/events/Makefile.am @@ -3,6 +3,8 @@ MAINTAINERCLEANFILES = Makefile.in EXTRA_DIST = \ AddNodeEvent.cpp \ AddNodeEvent.hpp \ + AddPortEvent.cpp \ + AddPortEvent.hpp \ AllNotesOffEvent.cpp \ AllNotesOffEvent.hpp \ ClearPatchEvent.cpp \ @@ -23,8 +25,6 @@ EXTRA_DIST = \ DeactivateEvent.hpp \ DestroyEvent.cpp \ DestroyEvent.hpp \ - DisablePatchEvent.cpp \ - DisablePatchEvent.hpp \ DisconnectNodeEvent.cpp \ DisconnectNodeEvent.hpp \ DisconnectPortEvent.cpp \ diff --git a/src/libs/gui/NodeModule.cpp b/src/libs/gui/NodeModule.cpp index 722cc08a..39df7151 100644 --- a/src/libs/gui/NodeModule.cpp +++ b/src/libs/gui/NodeModule.cpp @@ -38,6 +38,7 @@ namespace GUI { NodeModule::NodeModule(boost::shared_ptr canvas, SharedPtr node) : FlowCanvas::Module(canvas, node->path().name()) , _node(node) + , _slv2_ui(NULL) , _gui(NULL) , _gui_item(NULL) { @@ -90,14 +91,30 @@ NodeModule::create(boost::shared_ptr canvas, SharedPtr n for (MetadataMap::const_iterator m = node->metadata().begin(); m != node->metadata().end(); ++m) ret->set_metadata(m->first, m->second); - for (PortModelList::const_iterator p = node->ports().begin(); p != node->ports().end(); ++p) + uint32_t index = 0; + for (PortModelList::const_iterator p = node->ports().begin(); p != node->ports().end(); ++p) { ret->add_port(*p, false); + (*p)->signal_control.connect(sigc::bind<0>( + sigc::mem_fun(ret.get(), &NodeModule::control_change), index)); + ++index; + } ret->resize(); return ret; } + +void +NodeModule::control_change(uint32_t index, float control) +{ + if (_slv2_ui) { + const LV2UI_Descriptor* ui_descriptor = slv2_ui_instance_get_descriptor(_slv2_ui); + LV2UI_Handle ui_handle = slv2_ui_instance_get_handle(_slv2_ui); + ui_descriptor->port_event(ui_handle, index, 4, &control); + } +} + void NodeModule::embed_gui(bool embed) @@ -112,10 +129,10 @@ NodeModule::embed_gui(bool embed) if (!_gui_item) { cerr << "Embedding LV2 GUI" << endl; - SLV2UIInstance ui = _node->plugin()->ui(App::instance().engine().get(), _node.get()); - if (ui) { + _slv2_ui = _node->plugin()->ui(App::instance().engine().get(), _node.get()); + if (_slv2_ui) { cerr << "Found UI" << endl; - c_widget = (GtkWidget*)slv2_ui_instance_get_widget(ui); + c_widget = (GtkWidget*)slv2_ui_instance_get_widget(_slv2_ui); _gui = Glib::wrap(c_widget); assert(_gui); @@ -150,6 +167,10 @@ NodeModule::embed_gui(bool embed) _gui_item->raise_to_top(); _gui->signal_size_request().connect(sigc::mem_fun(this, &NodeModule::gui_size_request)); + + for (PortModelList::const_iterator p = _node->ports().begin(); p != _node->ports().end(); ++p) + if ((*p)->is_control() && (*p)->is_output()) + App::instance().engine()->enable_port_broadcasting((*p)->path()); } else { cerr << "*** Failed to create canvas item" << endl; @@ -166,8 +187,15 @@ NodeModule::embed_gui(bool embed) _gui = NULL; } + slv2_ui_instance_free(_slv2_ui); + _slv2_ui = NULL; + _ports_y_offset = 0; _width = 0; // resize() takes care of it.. + + for (PortModelList::const_iterator p = _node->ports().begin(); p != _node->ports().end(); ++p) + if ((*p)->is_control() && (*p)->is_output()) + App::instance().engine()->disable_port_broadcasting((*p)->path()); } resize(); diff --git a/src/libs/gui/NodeModule.hpp b/src/libs/gui/NodeModule.hpp index b35822f4..00e5835d 100644 --- a/src/libs/gui/NodeModule.hpp +++ b/src/libs/gui/NodeModule.hpp @@ -77,6 +77,8 @@ protected: void add_port(SharedPtr port, bool resize=true); void remove_port(SharedPtr port); + void control_change(uint32_t index, float control); + void embed_gui(bool embed); void gui_size_request(Gtk::Requisition* req); @@ -84,6 +86,7 @@ protected: SharedPtr _node; NodeMenu* _menu; + SLV2UIInstance _slv2_ui; Gtk::Widget* _gui; Gnome::Canvas::Widget* _gui_item; }; -- cgit v1.2.1