From 00b7385e4c1b8ab341f827323eeca77109349ef0 Mon Sep 17 00:00:00 2001 From: Paul Davis Date: Fri, 4 Mar 2016 16:44:30 -0500 Subject: correctly restore VCA-VCA slave/master relationships at session load time --- libs/ardour/ardour/gain_control.h | 4 +++- libs/ardour/ardour/vca_manager.h | 4 ++++ libs/ardour/gain_control.cc | 39 +++++++++++++++++++++++++++++---------- libs/ardour/vca_manager.cc | 6 ++++++ 4 files changed, 42 insertions(+), 11 deletions(-) diff --git a/libs/ardour/ardour/gain_control.h b/libs/ardour/ardour/gain_control.h index c44a76dd04..2b472dc8e0 100644 --- a/libs/ardour/ardour/gain_control.h +++ b/libs/ardour/ardour/gain_control.h @@ -91,12 +91,14 @@ class LIBARDOUR_API GainControl : public AutomationControl { typedef std::map Masters; Masters _masters; PBD::ScopedConnectionList masters_connections; - std::string _masters_state_string (); + std::string masters_string; + PBD::ScopedConnection vca_loaded_connection; gain_t get_value_locked () const; gain_t get_master_gain_locked () const; void master_going_away (boost::weak_ptr); void recompute_masters_ratios (double val); + void vcas_loaded(); void _set_value (double val, PBD::Controllable::GroupControlDisposition group_override); }; diff --git a/libs/ardour/ardour/vca_manager.h b/libs/ardour/ardour/vca_manager.h index 4e5b54f438..c51336b558 100644 --- a/libs/ardour/ardour/vca_manager.h +++ b/libs/ardour/ardour/vca_manager.h @@ -50,17 +50,21 @@ class VCAManager : public SessionHandleRef, public PBD::StatefulDestructible VCAList vcas() const; + PBD::Signal0 VCAsLoaded; PBD::Signal1 VCAAdded; PBD::Signal1 VCARemoved; XMLNode& get_state(); int set_state (XMLNode const&, int version); + bool vcas_loaded() const { return _vcas_loaded; } + static std::string xml_node_name; private: mutable Glib::Threads::Mutex lock; VCAList _vcas; + bool _vcas_loaded; void clear (); }; diff --git a/libs/ardour/gain_control.cc b/libs/ardour/gain_control.cc index b9c381c406..3eff20b1f1 100644 --- a/libs/ardour/gain_control.cc +++ b/libs/ardour/gain_control.cc @@ -348,22 +348,41 @@ GainControl::set_state (XMLNode const& node, int version) XMLProperty const* prop = node.property (X_("masters")); - /* XXX Problem here if we allow VCA's to be slaved to other VCA's .. we - * have to load all VCAs first, then call ::set_state() so that - * vca_by_number() will succeed. + /* Problem here if we allow VCA's to be slaved to other VCA's .. we + * have to load all VCAs first, then set up slave/master relationships + * once we have them all. */ if (prop) { - vector masters; - split (prop->value(), masters, ','); + masters_string = prop->value (); - for (vector::const_iterator m = masters.begin(); m != masters.end(); ++m) { - boost::shared_ptr vca = _session.vca_manager().vca_by_number (PBD::atoi (*m)); - if (vca) { - add_master (vca); - } + if (_session.vca_manager().vcas_loaded()) { + vcas_loaded (); + } else { + _session.vca_manager().VCAsLoaded.connect_same_thread (vca_loaded_connection, boost::bind (&GainControl::vcas_loaded, this)); } } return 0; } + +void +GainControl::vcas_loaded () +{ + if (masters_string.empty()) { + return; + } + + vector masters; + split (masters_string, masters, ','); + + for (vector::const_iterator m = masters.begin(); m != masters.end(); ++m) { + boost::shared_ptr vca = _session.vca_manager().vca_by_number (PBD::atoi (*m)); + if (vca) { + add_master (vca); + } + } + + vca_loaded_connection.disconnect (); + masters_string.clear (); +} diff --git a/libs/ardour/vca_manager.cc b/libs/ardour/vca_manager.cc index 9a96dc8a38..71c3fe8029 100644 --- a/libs/ardour/vca_manager.cc +++ b/libs/ardour/vca_manager.cc @@ -33,6 +33,7 @@ string VCAManager::xml_node_name (X_("VCAManager")); VCAManager::VCAManager (Session& s) : SessionHandleRef (s) + , _vcas_loaded (false) { } @@ -140,6 +141,8 @@ VCAManager::set_state (XMLNode const& node, int version) XMLNodeList const & children = node.children(); VCAList vcal; + _vcas_loaded = false; + for (XMLNodeList::const_iterator i = children.begin(); i != children.end(); ++i) { if ((*i)->name() == VCA::xml_node_name) { boost::shared_ptr vca = boost::shared_ptr (new VCA (_session, **i, version)); @@ -158,6 +161,9 @@ VCAManager::set_state (XMLNode const& node, int version) } } + _vcas_loaded = true; + + VCAsLoaded (); /* EMIT SIGNAL */ VCAAdded (vcal); /* EMIT SIGNAL */ return 0; -- cgit v1.2.3