From d4392b4a1b893253a05f806720b0a92282eba62e Mon Sep 17 00:00:00 2001 From: Ben Loftis Date: Sun, 27 Jun 2021 09:49:51 -0500 Subject: [PATCH] Playlist UI Tweaks: provide radio-buttons to switch ALL, Rec-armed, and grouped playlists (wip) --- gtk2_ardour/editor.cc | 14 ++-- gtk2_ardour/editor.h | 1 + gtk2_ardour/playlist_selector.cc | 27 +++++++- gtk2_ardour/playlist_selector.h | 5 ++ gtk2_ardour/public_editor.h | 7 ++ gtk2_ardour/route_ui.cc | 112 ++++++++++++------------------- gtk2_ardour/route_ui.h | 1 + 7 files changed, 92 insertions(+), 75 deletions(-) diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index ea3258aa0c..f6d9727043 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -4383,6 +4383,12 @@ Editor::stamp_new_playlist (string &name, string &pgroup, bool copy) return true; } +void +Editor::mapped_clear_playlist (RouteUI& rui) +{ + rui.clear_playlist (); +} + /** Clear the current playlist for a given track and also any others that belong * to the same active route group with the `select' property. * @param v Track. @@ -4399,15 +4405,15 @@ Editor::clear_grouped_playlists (RouteUI* rui) } void -Editor::mapped_use_new_playlist (RouteUI& rui, std::string name, string gid, bool copy, vector > const & playlists) +Editor::mapped_select_playlist_matching (RouteUI& rui, boost::weak_ptr pl) { - rui.use_new_playlist (name, gid, playlists, copy); + rui.select_playlist_matching (pl); } void -Editor::mapped_clear_playlist (RouteUI& rui) +Editor::mapped_use_new_playlist (RouteUI& rui, std::string name, string gid, bool copy, vector > const & playlists) { - rui.clear_playlist (); + rui.use_new_playlist (name, gid, playlists, copy); } void diff --git a/gtk2_ardour/editor.h b/gtk2_ardour/editor.h index 5268094077..227d974b14 100644 --- a/gtk2_ardour/editor.h +++ b/gtk2_ardour/editor.h @@ -783,6 +783,7 @@ private: void mapover_selected_routes (sigc::slot sl) const; void mapover_all_routes (sigc::slot sl) const; + void mapped_select_playlist_matching (RouteUI&, boost::weak_ptr pl); void mapped_use_new_playlist (RouteUI&, std::string name, std::string gid, bool copy, std::vector > const &); void mapped_clear_playlist (RouteUI&); diff --git a/gtk2_ardour/playlist_selector.cc b/gtk2_ardour/playlist_selector.cc index 14c92c1c8b..dc9ae894eb 100644 --- a/gtk2_ardour/playlist_selector.cc +++ b/gtk2_ardour/playlist_selector.cc @@ -68,10 +68,21 @@ PlaylistSelector::PlaylistSelector () scroller.add (tree); scroller.set_policy (POLICY_AUTOMATIC, POLICY_AUTOMATIC); + Gtk::RadioButtonGroup scope_group; + _scope_all_radio = manage (new RadioButton (scope_group, _("ALL tracks"))); + _scope_rec_radio = manage (new RadioButton (scope_group, _("Rec-armed tracks"))); + _scope_grp_radio = manage (new RadioButton (scope_group, _("Only this track/group"))); + + _scope_box = manage(new HBox()); + + _scope_box->pack_start (*_scope_all_radio, false, false); + _scope_box->pack_start (*_scope_rec_radio, false, false); + _scope_box->pack_start (*_scope_grp_radio, false, false); + get_vbox()->set_border_width (6); get_vbox()->set_spacing (12); - get_vbox()->pack_start (scroller); + get_vbox()->pack_start (*_scope_box); get_vbox()->show_all(); @@ -157,6 +168,12 @@ PlaylistSelector::redisplay() set_title (string_compose (_("Playlist for %1"), _rui->route()->name())); + if (_mode == plSelect) { + _scope_box->show(); + } else { + _scope_box->hide(); + } + clear_map (); if (model) { model->clear (); @@ -359,7 +376,13 @@ PlaylistSelector::selection_changed () _rui->track ()->use_playlist (_rui->is_audio_track () ? DataType::AUDIO : DataType::MIDI, pl); /* share the playlist and set ME as the owner */ break; case plSelect: - _rui->use_playlist (NULL, pl); //call route_ui::use_playlist because it is group-aware + if (_scope_all_radio->get_active()) { + PublicEditor::instance().mapover_all_routes (sigc::bind (sigc::mem_fun (PublicEditor::instance(), &PublicEditor::mapped_select_playlist_matching), pl)); + } else if (_scope_rec_radio->get_active()) { + PublicEditor::instance().mapover_armed_routes (sigc::bind (sigc::mem_fun (PublicEditor::instance(), &PublicEditor::mapped_select_playlist_matching), pl)); + } else { + PublicEditor::instance().mapover_grouped_routes (sigc::bind (sigc::mem_fun (PublicEditor::instance(), &PublicEditor::mapped_select_playlist_matching), pl), _rui, ARDOUR::Properties::group_select.property_id); + } break; } } diff --git a/gtk2_ardour/playlist_selector.h b/gtk2_ardour/playlist_selector.h index 4d75251ebf..bbb0954770 100644 --- a/gtk2_ardour/playlist_selector.h +++ b/gtk2_ardour/playlist_selector.h @@ -79,6 +79,11 @@ private: Gtk::ScrolledWindow scroller; TrackPlaylistMap trpl_map; + Gtk::HBox *_scope_box; + Gtk::RadioButton *_scope_all_radio; + Gtk::RadioButton *_scope_rec_radio; + Gtk::RadioButton *_scope_grp_radio; + RouteUI* _rui; plMode _mode; diff --git a/gtk2_ardour/public_editor.h b/gtk2_ardour/public_editor.h index 961e232b27..fc7ef86600 100644 --- a/gtk2_ardour/public_editor.h +++ b/gtk2_ardour/public_editor.h @@ -290,6 +290,13 @@ public: virtual void clear_playlist (boost::shared_ptr) = 0; virtual void clear_grouped_playlists (RouteUI*) = 0; + virtual void mapped_select_playlist_matching (RouteUI&, boost::weak_ptr pl) = 0; + + virtual void mapover_grouped_routes (sigc::slot sl, RouteUI*, PBD::PropertyID) const = 0; + virtual void mapover_armed_routes (sigc::slot sl) const = 0; + virtual void mapover_selected_routes (sigc::slot sl) const = 0; + virtual void mapover_all_routes (sigc::slot sl) const = 0; + virtual void new_playlists_for_all_tracks(bool copy) = 0; virtual void new_playlists_for_grouped_tracks(RouteUI* rui, bool copy) = 0; virtual void new_playlists_for_selected_tracks(bool copy) = 0; diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 58a34f02ce..d1e6b6af2d 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -2549,90 +2549,64 @@ RouteUI::build_playlist_menu () void RouteUI::use_playlist (RadioMenuItem *item, boost::weak_ptr wpl) { - assert (is_track()); - // exit if we were triggered by deactivating the old playlist if (item && !item->get_active()) { return; } + select_playlist_matching(wpl); +} + + +void +RouteUI::select_playlist_matching (boost::weak_ptr wpl) +{ + if (!is_track()) { + return; + } + boost::shared_ptr pl (wpl.lock()); if (!pl) { return; } - if (track()->playlist() == pl) { - // exit when use_playlist is called by the creation of the playlist menu - // or the playlist choice is unchanged + if (track()->freeze_state() == Track::Frozen) { + /* Don't change playlists of frozen tracks */ return; } - track()->use_playlist (track()->data_type(), pl); - - RouteGroup* rg = route_group(); - - if (rg && rg->is_active() && rg->enabled_property (ARDOUR::Properties::group_select.property_id)) { - - std::string pgrp_id = pl->pgroup_id(); - if (pgrp_id.length()>0) { //easy: find other pl's with the same group id - boost::shared_ptr rl (rg->route_list()); - for (RouteList::const_iterator i = rl->begin(); i != rl->end(); ++i) { - if ((*i) == this->route()) { - continue; - } - if ((*i)->route_group() != rg) { - continue; - } - boost::shared_ptr track = boost::dynamic_pointer_cast(*i); - if (!track) { - continue; - } - boost::shared_ptr ipl = session()->playlists()->for_pgroup(pgrp_id, track->id()); - if (ipl) { - track->use_playlist(track->data_type(), ipl); - } - } - } else { //fallback to prior behavior ... try to find matching names /*DEPRECATED*/ - std::string take_name = pl->name(); - std::string group_string = "." + rg->name() + "."; - - std::string::size_type idx = take_name.find(group_string); - - if (idx == std::string::npos) - return; - - take_name = take_name.substr(idx + group_string.length()); // find the bit containing the take number / name - - boost::shared_ptr rl (rg->route_list()); - for (RouteList::const_iterator i = rl->begin(); i != rl->end(); ++i) { - if ((*i) == this->route()) { - continue; - } - - std::string playlist_name = (*i)->name()+group_string+take_name; - - boost::shared_ptr track = boost::dynamic_pointer_cast(*i); - if (!track) { - continue; - } - - if (track->freeze_state() == Track::Frozen) { - /* Don't change playlists of frozen tracks */ - continue; - } - - boost::shared_ptr ipl = session()->playlists()->by_name(playlist_name); - if (!ipl) { - // No playlist for this track for this take yet, make it - track->use_default_new_playlist(); - track->playlist()->set_name(playlist_name); - } else { - track->use_playlist(track->data_type(), ipl); - } - } - } //fallback + if (track()->playlist() == pl) { + /* already selected; nothing to do */ + return; } + + std::string pgrp_id = pl->pgroup_id(); + boost::shared_ptr ipl = session()->playlists()->for_pgroup(pgrp_id, track()->id()); + if (ipl) { + //found a playlist that matches the pgroup_id, use it + track()->use_playlist (track()->data_type(), ipl); + } else { //fallback to prior behavior ... try to find matching names /*DEPRECATED*/ + + std::string take_name = pl->name(); + std::string group_name; + if (track()->route_group()) { + group_name = track()->route_group()->name(); + } + std::string group_string = "." + group_name + "."; + + std::string::size_type idx = take_name.find(group_string); + + if (idx != std::string::npos) { + take_name = take_name.substr(idx + group_string.length()); // find the bit containing the take number / name + std::string playlist_name = track()->name()+group_string+take_name; + + boost::shared_ptr ipl = session()->playlists()->by_name(playlist_name); + if (ipl) { + track()->use_playlist(track()->data_type(), ipl); + } + } + } //fallback } void diff --git a/gtk2_ardour/route_ui.h b/gtk2_ardour/route_ui.h index 20c349050d..7337cab7ea 100644 --- a/gtk2_ardour/route_ui.h +++ b/gtk2_ardour/route_ui.h @@ -163,6 +163,7 @@ public: void clear_playlist (); void use_playlist (Gtk::RadioMenuItem* item, boost::weak_ptr wpl); + void select_playlist_matching (boost::weak_ptr wpl); void show_playlist_selector (); /* used by EditorRoutes */