Add method to find subgroup_bus
[ardour.git] / libs / ardour / selection.cc
index 876056c3da81a7b55cfb3cebc46f7ffe859f1b86..5bd05b99f754d529dbd484e035b6defa147d0767 100644 (file)
@@ -17,6 +17,8 @@
 
 */
 
+#include <vector>
+
 #include "pbd/compose.h"
 #include "pbd/signals.h"
 
@@ -79,6 +81,13 @@ CoreSelection::add (boost::shared_ptr<Stripable> s, boost::shared_ptr<Automation
 
        if (send) {
                send_selection_change ();
+               /* send per-object signal to notify interested parties
+                  the selection status has changed
+               */
+               if (s) {
+                       PropertyChange pc (Properties::selected);
+                       s->presentation_info().PropertyChanged (pc);
+               }
        }
 }
 
@@ -102,6 +111,13 @@ CoreSelection::remove (boost::shared_ptr<Stripable> s, boost::shared_ptr<Automat
 
        if (send) {
                send_selection_change ();
+               /* send per-object signal to notify interested parties
+                  the selection status has changed
+               */
+               if (s) {
+                       PropertyChange pc (Properties::selected);
+                       s->presentation_info().PropertyChanged (pc);
+               }
        }
 }
 
@@ -123,20 +139,39 @@ CoreSelection::set (boost::shared_ptr<Stripable> s, boost::shared_ptr<Automation
        }
 
        send_selection_change ();
+
+       /* send per-object signal to notify interested parties
+          the selection status has changed
+       */
+       if (s) {
+               PropertyChange pc (Properties::selected);
+               s->presentation_info().PropertyChanged (pc);
+       }
 }
 
 void
 CoreSelection::clear_stripables ()
 {
        bool send = false;
+       std::vector<boost::shared_ptr<Stripable> > s;
 
        DEBUG_TRACE (DEBUG::Selection, "clearing s/c selection\n");
-
        {
                Glib::Threads::RWLock::WriterLock lm (_lock);
 
                if (!_stripables.empty()) {
+
+                       s.reserve (_stripables.size());
+
+                       for (SelectedStripables::const_iterator x = _stripables.begin(); x != _stripables.end(); ++x) {
+                               boost::shared_ptr<Stripable> sp = session.stripable_by_id ((*x).stripable);
+                               if (sp) {
+                                       s.push_back (sp);
+                               }
+                       }
+
                        _stripables.clear ();
+
                        send = true;
                        DEBUG_TRACE (DEBUG::Selection, "cleared s/c selection\n");
                }
@@ -144,6 +179,13 @@ CoreSelection::clear_stripables ()
 
        if (send) {
                send_selection_change ();
+
+               PropertyChange pc (Properties::selected);
+
+               for (std::vector<boost::shared_ptr<Stripable> >::iterator ss = s.begin(); ss != s.end(); ++ss) {
+                       (*ss)->presentation_info().PropertyChanged (pc);
+               }
+
        }
 }
 
@@ -217,9 +259,11 @@ CoreSelection::get_stripables (StripableAutomationControls& sc) const
                boost::shared_ptr<AutomationControl> c;
 
                if (!s) {
+                       /* some global automation control, not owned by a Stripable */
                        c = session.automation_control_by_id ((*x).controllable);
                } else {
-                       c = s->automation_control ((*x).controllable);
+                       /* automation control owned by a Stripable or one of its children */
+                       c = s->automation_control_recurse ((*x).controllable);
                }
 
                if (s || c) {
@@ -249,10 +293,14 @@ CoreSelection::remove_stripable_by_id (PBD::ID const & id)
 {
        Glib::Threads::RWLock::WriterLock lm (_lock);
 
-       for (SelectedStripables::iterator x = _stripables.begin(); x != _stripables.end(); ++x) {
+       for (SelectedStripables::iterator x = _stripables.begin(); x != _stripables.end(); ) {
                if ((*x).stripable == id) {
-                       _stripables.erase (x);
-                       return;
+                       _stripables.erase (x++);
+                       /* keep going because there may be more than 1 pair of
+                          stripable/automation-control in the selection.
+                       */
+               } else {
+                       ++x;
                }
        }
 }
@@ -310,8 +358,6 @@ CoreSelection::set_state (const XMLNode& node, int /* version */)
                _stripables.insert (ss);
        }
 
-       std::cerr << "set state: " << _stripables.size() << std::endl;
-
        return 0;
 }
 
@@ -321,4 +367,3 @@ CoreSelection::selected () const
        Glib::Threads::RWLock::ReaderLock lm (_lock);
        return _stripables.size();
 }
-