X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;f=gtk2_ardour%2Froute_time_axis.cc;h=e723aeee4005ce55bb65e81609ca8fa43eaf296c;hb=89d6f40e33933b12a40079e391a96856bfa79e2a;hp=d06c2a6ae74aaf8217b69aab0f48b11786076c6f;hpb=f9e3a8b59fe3af25665d257601874166c8f722d6;p=ardour.git diff --git a/gtk2_ardour/route_time_axis.cc b/gtk2_ardour/route_time_axis.cc index d06c2a6ae7..e723aeee40 100644 --- a/gtk2_ardour/route_time_axis.cc +++ b/gtk2_ardour/route_time_axis.cc @@ -113,14 +113,12 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session* sess, boost::sh , playlist_button (_("p")) , automation_button (_("a")) , gm (sess, slider, true, 115) - , _ignore_track_mode_change (false) { gm.set_controls (_route, _route->shared_peak_meter(), _route->amp()); gm.get_level_meter().set_no_show_all(); gm.get_level_meter().setup_meters(50); _has_state = true; - playlist_menu = 0; playlist_action_menu = 0; automation_action_menu = 0; plugins_submenu_item = 0; @@ -136,9 +134,6 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session* sess, boost::sh timestretch_rect = 0; no_redraw = false; - destructive_track_mode_item = 0; - normal_track_mode_item = 0; - non_layered_track_mode_item = 0; ignore_toggle = false; @@ -217,7 +212,6 @@ RouteTimeAxisView::RouteTimeAxisView (PublicEditor& ed, Session* sess, boost::sh if (is_track()) { - track()->TrackModeChanged.connect (*this, invalidator (*this), boost::bind (&RouteTimeAxisView::track_mode_changed, this), gui_context()); track()->FreezeChange.connect (*this, invalidator (*this), boost::bind (&RouteTimeAxisView::map_frozen, this), gui_context()); track()->SpeedChanged.connect (*this, invalidator (*this), boost::bind (&RouteTimeAxisView::speed_changed, this), gui_context()); @@ -251,9 +245,6 @@ RouteTimeAxisView::~RouteTimeAxisView () delete *i; } - delete playlist_menu; - playlist_menu = 0; - delete playlist_action_menu; playlist_action_menu = 0; @@ -289,8 +280,8 @@ RouteTimeAxisView::route_group_click (GdkEventButton *ev) return false; } - route_group_menu->rebuild (_route->route_group ()); - route_group_menu->popup (ev->button, ev->time); + route_group_menu->build (_route->route_group ()); + route_group_menu->menu()->popup (ev->button, ev->time); return false; } @@ -443,6 +434,9 @@ RouteTimeAxisView::build_display_menu () items.push_back (MenuElem (_("Color..."), sigc::mem_fun (*this, &RouteUI::choose_color))); + if (_size_menu) { + detach_menu (*_size_menu); + } build_size_menu (); items.push_back (MenuElem (_("Height"), *_size_menu)); @@ -450,10 +444,7 @@ RouteTimeAxisView::build_display_menu () if (!Profile->get_sae()) { items.push_back (MenuElem (_("Remote Control ID..."), sigc::mem_fun (*this, &RouteUI::open_remote_control_id_dialog))); - /* rebuild this every time */ - build_automation_action_menu (); - detach_menu (*automation_action_menu); - items.push_back (MenuElem (_("Automation"), *automation_action_menu)); + items.back().set_sensitive (_editor.get_selection().tracks.size() <= 1); items.push_back (SeparatorElem()); } @@ -462,17 +453,55 @@ RouteTimeAxisView::build_display_menu () if (is_track()) { - Menu *layers_menu = manage(new Menu); + Menu* layers_menu = manage (new Menu); MenuList &layers_items = layers_menu->items(); layers_menu->set_name("ArdourContextMenu"); RadioMenuItem::Group layers_group; - layers_items.push_back(RadioMenuElem (layers_group, _("Overlaid"), - sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_layer_display), Overlaid))); - layers_items.push_back(RadioMenuElem (layers_group, _("Stacked"), - sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_layer_display), Stacked))); + /* Find out how many overlaid/stacked tracks we have in the selection */ + + int overlaid = 0; + int stacked = 0; + TrackSelection const & s = _editor.get_selection().tracks; + for (TrackSelection::const_iterator i = s.begin(); i != s.end(); ++i) { + StreamView* v = (*i)->view (); + if (!v) { + continue; + } + + switch (v->layer_display ()) { + case Overlaid: + ++overlaid; + break; + case Stacked: + ++stacked; + break; + } + } + /* We're not connecting to signal_toggled() here; in the case where these two items are + set to be in the `inconsistent' state, it seems that one or other will end up active + as well as inconsistent (presumably due to the RadioMenuItem::Group). Then when you + select the active one, no toggled signal is emitted so nothing happens. + */ + + layers_items.push_back (RadioMenuElem (layers_group, _("Overlaid"))); + RadioMenuItem* i = dynamic_cast (&layers_items.back ()); + i->set_active (overlaid != 0 && stacked == 0); + i->set_inconsistent (overlaid != 0 && stacked != 0); + i->signal_activate().connect (sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_layer_display), Overlaid, true)); + + layers_items.push_back ( + RadioMenuElem (layers_group, _("Stacked"), + sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_layer_display), Stacked, true)) + ); + + i = dynamic_cast (&layers_items.back ()); + i->signal_activate().connect (sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_layer_display), Stacked, true)); + i->set_active (overlaid == 0 && stacked != 0); + i->set_inconsistent (overlaid != 0 && stacked != 0); + items.push_back (MenuElem (_("Layers"), *layers_menu)); if (!Profile->get_sae()) { @@ -482,23 +511,41 @@ RouteTimeAxisView::build_display_menu () alignment_menu->set_name ("ArdourContextMenu"); RadioMenuItem::Group align_group; - - alignment_items.push_back (RadioMenuElem (align_group, _("Align With Existing Material"), - sigc::bind (sigc::mem_fun(*this, &RouteTimeAxisView::set_align_style), ExistingMaterial))); - align_existing_item = dynamic_cast(&alignment_items.back()); - if (track()->alignment_style() == ExistingMaterial) { - align_existing_item->set_active(); + + /* Same verbose hacks as for the layering options above */ + + int existing = 0; + int capture = 0; + TrackSelection const & s = _editor.get_selection().tracks; + for (TrackSelection::const_iterator i = s.begin(); i != s.end(); ++i) { + RouteTimeAxisView* r = dynamic_cast (*i); + if (!r || !r->is_track ()) { + continue; + } + + switch (r->track()->alignment_style()) { + case ExistingMaterial: + ++existing; + break; + case CaptureTime: + ++capture; + break; + } } - alignment_items.push_back (RadioMenuElem (align_group, _("Align With Capture Time"), - sigc::bind (sigc::mem_fun(*this, &RouteTimeAxisView::set_align_style), CaptureTime))); - align_capture_item = dynamic_cast(&alignment_items.back()); - if (track()->alignment_style() == CaptureTime) { - align_capture_item->set_active(); - } + alignment_items.push_back (RadioMenuElem (align_group, _("Align With Existing Material"))); + RadioMenuItem* i = dynamic_cast (&alignment_items.back()); + i->signal_activate().connect (sigc::bind (sigc::mem_fun(*this, &RouteTimeAxisView::set_align_style), ExistingMaterial, true)); + i->set_active (existing != 0 && capture == 0); + i->set_inconsistent (existing != 0 && capture != 0); + + alignment_items.push_back (RadioMenuElem (align_group, _("Align With Capture Time"))); + i = dynamic_cast (&alignment_items.back()); + i->signal_activate().connect (sigc::bind (sigc::mem_fun(*this, &RouteTimeAxisView::set_align_style), CaptureTime, true)); + i->set_active (existing == 0 && capture != 0); + i->set_inconsistent (existing != 0 && capture != 0); items.push_back (MenuElem (_("Alignment"), *alignment_menu)); - track()->AlignmentStyleChanged.connect (route_connections, invalidator (*this), boost::bind (&RouteTimeAxisView::align_style_changed, this), gui_context()); Menu* mode_menu = manage (new Menu); MenuList& mode_items = mode_menu->items (); @@ -506,36 +553,46 @@ RouteTimeAxisView::build_display_menu () RadioMenuItem::Group mode_group; - mode_items.push_back (RadioMenuElem (mode_group, _("Normal Mode"), sigc::bind ( - sigc::mem_fun (*this, &RouteTimeAxisView::set_track_mode), - ARDOUR::Normal))); - normal_track_mode_item = dynamic_cast(&mode_items.back()); + int normal = 0; + int tape = 0; + int non_layered = 0; - mode_items.push_back (RadioMenuElem (mode_group, _("Tape Mode"), sigc::bind ( - sigc::mem_fun (*this, &RouteTimeAxisView::set_track_mode), - ARDOUR::Destructive))); - destructive_track_mode_item = dynamic_cast(&mode_items.back()); + for (TrackSelection::const_iterator i = s.begin(); i != s.end(); ++i) { + RouteTimeAxisView* r = dynamic_cast (*i); + if (!r || !r->is_track ()) { + continue; + } + + switch (r->track()->mode()) { + case Normal: + ++normal; + break; + case Destructive: + ++tape; + break; + case NonLayered: + ++non_layered; + break; + } + } - mode_items.push_back (RadioMenuElem (mode_group, _("Non-Layered Mode"), - sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_track_mode), ARDOUR::NonLayered))); - non_layered_track_mode_item = dynamic_cast(&mode_items.back()); + mode_items.push_back (RadioMenuElem (mode_group, _("Normal Mode"))); + i = dynamic_cast (&mode_items.back ()); + i->signal_activate().connect (sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_track_mode), ARDOUR::Normal, true)); + i->set_active (normal != 0 && tape == 0 && non_layered == 0); + i->set_inconsistent (normal != 0 && (tape != 0 || non_layered != 0)); + mode_items.push_back (RadioMenuElem (mode_group, _("Tape Mode"))); + i = dynamic_cast (&mode_items.back ()); + i->signal_activate().connect (sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_track_mode), ARDOUR::Destructive, true)); + i->set_active (normal == 0 && tape != 0 && non_layered == 0); + i->set_inconsistent (tape != 0 && (normal != 0 || non_layered != 0)); - _ignore_track_mode_change = true; - - switch (track()->mode()) { - case ARDOUR::Destructive: - destructive_track_mode_item->set_active (); - break; - case ARDOUR::Normal: - normal_track_mode_item->set_active (); - break; - case ARDOUR::NonLayered: - non_layered_track_mode_item->set_active (); - break; - } - - _ignore_track_mode_change = false; + mode_items.push_back (RadioMenuElem (mode_group, _("Non-Layered Mode"))); + i = dynamic_cast (&mode_items.back ()); + i->signal_activate().connect (sigc::bind (sigc::mem_fun (*this, &RouteTimeAxisView::set_track_mode), ARDOUR::NonLayered, true)); + i->set_active (normal == 0 && tape == 0 && non_layered != 0); + i->set_inconsistent (non_layered != 0 && (normal != 0 || tape != 0)); items.push_back (MenuElem (_("Mode"), *mode_menu)); } @@ -549,9 +606,11 @@ RouteTimeAxisView::build_display_menu () build_playlist_menu (); items.push_back (MenuElem (_("Playlist"), *playlist_action_menu)); + items.back().set_sensitive (_editor.get_selection().tracks.size() <= 1); - route_group_menu->rebuild (_route->route_group ()); - items.push_back (MenuElem (_("Route Group"), *route_group_menu)); + route_group_menu->detach (); + route_group_menu->build (_route->route_group ()); + items.push_back (MenuElem (_("Route Group"), *route_group_menu->menu ())); build_automation_action_menu (); items.push_back (MenuElem (_("Automation"), *automation_action_menu)); @@ -573,108 +632,42 @@ RouteTimeAxisView::build_display_menu () } } -static bool __reset_item (RadioMenuItem* item, RadioMenuItem* item_2) -{ - item->set_active (); - item_2->set_active (); - return false; -} - void -RouteTimeAxisView::set_track_mode (TrackMode mode) +RouteTimeAxisView::set_track_mode (TrackMode mode, bool apply_to_selection) { - if (_ignore_track_mode_change) { - return; - } - - RadioMenuItem* item; - RadioMenuItem* other_item; - RadioMenuItem* other_item_2; - - switch (mode) { - case ARDOUR::Normal: - item = normal_track_mode_item; - other_item = non_layered_track_mode_item; - other_item_2 = destructive_track_mode_item; - break; - case ARDOUR::NonLayered: - item = non_layered_track_mode_item; - other_item = normal_track_mode_item; - other_item_2 = destructive_track_mode_item; - break; - case ARDOUR::Destructive: - item = destructive_track_mode_item; - other_item = normal_track_mode_item; - other_item_2 = non_layered_track_mode_item; - break; - default: - fatal << string_compose (_("programming error: %1 %2"), "illegal track mode in RouteTimeAxisView::set_track_mode", mode) << endmsg; - /*NOTREACHED*/ - return; - } - - if (item && other_item && other_item_2 && track()->mode() != mode) { - _set_track_mode (track().get(), mode, other_item, other_item_2); - } -} - -void -RouteTimeAxisView::_set_track_mode (Track* track, TrackMode mode, RadioMenuItem* reset_item, RadioMenuItem* reset_item_2) -{ - bool needs_bounce; + if (apply_to_selection) { + _editor.get_selection().tracks.foreach_route_time_axis (boost::bind (&RouteTimeAxisView::set_track_mode, _1, mode, false)); + } else { - if (!track->can_use_mode (mode, needs_bounce)) { + bool needs_bounce; - if (!needs_bounce) { - /* cannot be done */ - Glib::signal_idle().connect (sigc::bind (sigc::ptr_fun (__reset_item), reset_item, reset_item_2)); - return; - } else { - cerr << "would bounce this one\n"; - /* XXX: radio menu item becomes inconsistent with track state in this case */ - return; + if (!track()->can_use_mode (mode, needs_bounce)) { + + if (!needs_bounce) { + /* cannot be done */ + return; + } else { + cerr << "would bounce this one\n"; + return; + } } + + track()->set_mode (mode); + + rec_enable_button->remove (); + + switch (mode) { + case ARDOUR::NonLayered: + case ARDOUR::Normal: + rec_enable_button->add (*(manage (new Image (::get_icon (X_("record_normal_red")))))); + break; + case ARDOUR::Destructive: + rec_enable_button->add (*(manage (new Image (::get_icon (X_("record_tape_red")))))); + break; + } + + rec_enable_button->show_all (); } - - track->set_mode (mode); - - rec_enable_button->remove (); - - switch (mode) { - case ARDOUR::NonLayered: - case ARDOUR::Normal: - rec_enable_button->add (*(manage (new Image (::get_icon (X_("record_normal_red")))))); - break; - case ARDOUR::Destructive: - rec_enable_button->add (*(manage (new Image (::get_icon (X_("record_tape_red")))))); - break; - } - - rec_enable_button->show_all (); -} - -void -RouteTimeAxisView::track_mode_changed () -{ - RadioMenuItem* item; - - switch (track()->mode()) { - case ARDOUR::Normal: - item = normal_track_mode_item; - break; - case ARDOUR::NonLayered: - item = non_layered_track_mode_item; - break; - case ARDOUR::Destructive: - item = destructive_track_mode_item; - break; - default: - fatal << string_compose (_("programming error: %1 %2"), "illegal track mode in RouteTimeAxisView::set_track_mode", track()->mode()) << endmsg; - /*NOTREACHED*/ - return; - } - - item->set_active (); } void @@ -903,42 +896,14 @@ RouteTimeAxisView::set_samples_per_unit (double spu) } void -RouteTimeAxisView::align_style_changed () +RouteTimeAxisView::set_align_style (AlignStyle style, bool apply_to_selection) { - switch (track()->alignment_style()) { - case ExistingMaterial: - if (!align_existing_item->get_active()) { - align_existing_item->set_active(); - } - break; - case CaptureTime: - if (!align_capture_item->get_active()) { - align_capture_item->set_active(); + if (apply_to_selection) { + _editor.get_selection().tracks.foreach_route_time_axis (boost::bind (&RouteTimeAxisView::set_align_style, _1, style, false)); + } else { + if (track ()) { + track()->set_align_style (style); } - break; - } -} - -void -RouteTimeAxisView::set_align_style (AlignStyle style) -{ - RadioMenuItem* item; - - switch (style) { - case ExistingMaterial: - item = align_existing_item; - break; - case CaptureTime: - item = align_capture_item; - break; - default: - fatal << string_compose (_("programming error: %1 %2"), "illegal align style in RouteTimeAxisView::set_align_style", style) << endmsg; - /*NOTREACHED*/ - return; - } - - if (item->get_active()) { - track()->set_align_style (style); } } @@ -1434,8 +1399,6 @@ RouteTimeAxisView::build_playlist_menu () playlist_action_menu->set_name ("ArdourContextMenu"); playlist_items.clear(); - delete playlist_menu; - vector > playlists, playlists_tr; boost::shared_ptr tr = track(); RadioMenuItem::Group playlist_group; @@ -2162,14 +2125,19 @@ RouteTimeAxisView::update_rec_display () } void -RouteTimeAxisView::set_layer_display (LayerDisplay d) +RouteTimeAxisView::set_layer_display (LayerDisplay d, bool apply_to_selection) { - if (_view) { - _view->set_layer_display (d); + if (apply_to_selection) { + _editor.get_selection().tracks.foreach_route_time_axis (boost::bind (&RouteTimeAxisView::set_layer_display, _1, d, false)); + } else { + + if (_view) { + _view->set_layer_display (d); + } + + ensure_xml_node (); + xml_node->add_property (N_("layer-display"), enum_2_string (d)); } - - ensure_xml_node (); - xml_node->add_property (N_("layer-display"), enum_2_string (d)); } LayerDisplay @@ -2415,6 +2383,10 @@ RouteTimeAxisView::create_gain_automation_child (const Evoral::Parameter& param, false, parent_canvas, _route->amp()->describe_parameter(param))); + + if (_view) { + _view->foreach_regionview (sigc::mem_fun (*gain_track.get(), &TimeAxisView::add_ghost)); + } add_automation_child (Evoral::Parameter(GainAutomation), gain_track, show); }