X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;f=gtk2_ardour%2Feditor.cc;h=4ce3ac55b81af67407a42e6807c060bf1fa5b5cf;hb=906f7e1edd412c35fe16939f3599c76aa0735a89;hp=05146077e26e77bc306d2f1b48a14b69de84aef1;hpb=bac7a13d0f5866ce6e771616f9faf8fb9fc73260;p=ardour.git diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 05146077e2..4ce3ac55b8 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -72,11 +72,13 @@ #include "ardour/lmath.h" #include "ardour/location.h" #include "ardour/profile.h" +#include "ardour/route.h" #include "ardour/route_group.h" #include "ardour/session_playlists.h" #include "ardour/tempo.h" #include "ardour/utils.h" #include "ardour/vca_manager.h" +#include "ardour/vca.h" #include "canvas/debug.h" #include "canvas/text.h" @@ -124,6 +126,7 @@ #include "region_layering_order_editor.h" #include "rgb_macros.h" #include "rhythm_ferret.h" +#include "route_sorter.h" #include "selection.h" #include "simple_progress_dialog.h" #include "sfdb_ui.h" @@ -671,6 +674,7 @@ Editor::Editor () _notebook_shrunk = string_is_affirmative (prop->value ()); } + editor_summary_pane.set_check_divider_position (true); editor_summary_pane.add (edit_packer); Button* summary_arrows_left_left = manage (new Button); @@ -715,6 +719,7 @@ Editor::Editor () editor_summary_pane.add (_summary_hbox); } + edit_pane.set_check_divider_position (true); edit_pane.add (editor_summary_pane); if (!ARDOUR::Profile->get_trx()) { edit_pane.add (_the_notebook); @@ -726,19 +731,23 @@ Editor::Editor () float fract; - if (!settings || ((prop = settings->property ("edit-horizontal-pane-pos")) == 0) || ((fract = atof (prop->value())) > 1.0)) { - /* initial allocation is 90% to canvas, 10% to notebook */ - edit_pane.set_divider (0, 0.90); - } else { - edit_pane.set_divider (0, fract); - } + { + LocaleGuard lg; - if (!settings || ((prop = settings->property ("edit-vertical-pane-pos")) == 0) || ((fract = atof (prop->value())) > 1.0)) { - /* initial allocation is 90% to canvas, 10% to summary */ - editor_summary_pane.set_divider (0, 0.90); - } else { + if (!settings || ((prop = settings->property ("edit-horizontal-pane-pos")) == 0) || ((fract = atof (prop->value())) > 1.0)) { + /* initial allocation is 90% to canvas, 10% to notebook */ + edit_pane.set_divider (0, 0.90); + } else { + edit_pane.set_divider (0, fract); + } + + if (!settings || ((prop = settings->property ("edit-vertical-pane-pos")) == 0) || ((fract = atof (prop->value())) > 1.0)) { + /* initial allocation is 90% to canvas, 10% to summary */ + editor_summary_pane.set_divider (0, 0.90); + } else { - editor_summary_pane.set_divider (0, fract); + editor_summary_pane.set_divider (0, fract); + } } top_hbox.pack_start (toolbar_frame); @@ -796,12 +805,6 @@ Editor::Editor () ControlProtocol::VerticalZoomInSelected.connect (*this, invalidator (*this), boost::bind (&Editor::control_vertical_zoom_in_selected, this), gui_context()); ControlProtocol::VerticalZoomOutSelected.connect (*this, invalidator (*this), boost::bind (&Editor::control_vertical_zoom_out_selected, this), gui_context()); - ControlProtocol::AddStripableToSelection.connect (*this, invalidator (*this), boost::bind (&Editor::control_select, this, _1, Selection::Add), gui_context()); - ControlProtocol::RemoveStripableFromSelection.connect (*this, invalidator (*this), boost::bind (&Editor::control_select, this, _1, Selection::Toggle), gui_context()); - ControlProtocol::SetStripableSelection.connect (*this, invalidator (*this), boost::bind (&Editor::control_select, this, _1, Selection::Set), gui_context()); - ControlProtocol::ToggleStripableSelection.connect (*this, invalidator (*this), boost::bind (&Editor::control_select, this, _1, Selection::Toggle), gui_context()); - ControlProtocol::ClearStripableSelection.connect (*this, invalidator (*this), boost::bind (&Editor::control_unselect, this), gui_context()); - BasicUI::AccessAction.connect (*this, invalidator (*this), boost::bind (&Editor::access_action, this, _1, _2), gui_context()); /* handle escape */ @@ -1003,63 +1006,6 @@ Editor::control_unselect () selection->clear_tracks (); } -void -Editor::control_select (PresentationInfo::global_order_t global_order, Selection::Operation op) -{ - /* handles the (static) signal from the ControlProtocol class that - * requests setting the selected track to a given RID - */ - - if (!_session) { - return; - } - - PresentationInfo::Flag select_flags; - - if (global_order & ~0xffffffff) { - /* some flags are set, so the PresentationInfo constructor - * will use them - */ - select_flags = PresentationInfo::Flag (0); - } else { - /* no type flags set in the global order ID, so assume caller - * wants to select a Route - */ - select_flags = PresentationInfo::Route; - } - - PresentationInfo pi (global_order, select_flags); - boost::shared_ptr s = _session->get_remote_nth_stripable (pi.group_order(), pi.flags()); - - /* selected object may not be a Route */ - - boost::shared_ptr r = boost::dynamic_pointer_cast (s); - - if (!r) { - return; - } - - TimeAxisView* tav = axis_view_from_route (r); - - if (tav) { - switch (op) { - case Selection::Add: - selection->add (tav); - break; - case Selection::Toggle: - selection->toggle (tav); - break; - case Selection::Extend: - break; - case Selection::Set: - selection->set (tav); - break; - } - } else { - selection->clear_tracks (); - } -} - void Editor::control_step_tracks_up () { @@ -1430,6 +1376,25 @@ Editor::set_session (Session *t) break; } + /* catch up on selection of stripables (other selection state is lost + * when a session is closed + */ + + StripableList sl; + TrackViewList tl; + _session->get_stripables (sl); + for (StripableList::const_iterator s = sl.begin(); s != sl.end(); ++s) { + if ((*s)->presentation_info().selected()) { + RouteTimeAxisView* rtav = get_route_view_by_route_id ((*s)->id()); + if (rtav) { + tl.push_back (rtav); + } + } + } + if (!tl.empty()) { + selection->set (tl); + } + /* register for undo history */ _session->register_with_memento_command_factory(id(), this); _session->register_with_memento_command_factory(_selection_memento->id(), _selection_memento); @@ -2368,6 +2333,8 @@ Editor::set_state (const XMLNode& node, int version) if ((prop = node.property ("zoom-focus"))) { zoom_focus_selection_done ((ZoomFocus) string_2_enum (prop->value(), zoom_focus)); + } else { + zoom_focus_selection_done (zoom_focus); } if ((prop = node.property ("zoom"))) { @@ -2385,6 +2352,8 @@ Editor::set_state (const XMLNode& node, int version) if ((prop = node.property ("snap-to"))) { snap_type_selection_done ((SnapType) string_2_enum (prop->value(), _snap_type)); set_snap_to ((SnapType) string_2_enum (prop->value(), _snap_type)); + } else { + set_snap_to (_snap_type); } if ((prop = node.property ("snap-mode"))) { @@ -2394,6 +2363,8 @@ Editor::set_state (const XMLNode& node, int version) * which does not trigger set_text(). */ set_snap_mode ((SnapMode) string_2_enum (prop->value(), _snap_mode)); + } else { + set_snap_mode (_snap_mode); } if ((prop = node.property ("internal-snap-to"))) { @@ -2446,6 +2417,8 @@ Editor::set_state (const XMLNode& node, int version) if ((prop = node.property ("edit-point"))) { set_edit_point_preference ((EditPoint) string_2_enum (prop->value(), _edit_point), true); + } else { + set_edit_point_preference (_edit_point); } if ((prop = node.property ("show-measures"))) { @@ -4048,6 +4021,47 @@ Editor::get_grid_beat_divisions(framepos_t position) return 0; } +/** returns the current musical grid divisiions using the supplied modifier mask from a GtkEvent. + if the grid is non-musical, returns 0. + if the grid is snapped to bars, returns -1. + @param event_state the current keyboard modifier mask. +*/ +unsigned +Editor::get_grid_music_divisions (uint32_t event_state) +{ + if (snap_mode() == Editing::SnapOff && !ArdourKeyboard::indicates_snap (event_state)) { + return 0; + } + + if (snap_mode() != Editing::SnapOff && ArdourKeyboard::indicates_snap (event_state)) { + return 0; + } + + switch (_snap_type) { + case SnapToBeatDiv128: return 128; + case SnapToBeatDiv64: return 64; + case SnapToBeatDiv32: return 32; + case SnapToBeatDiv28: return 28; + case SnapToBeatDiv24: return 24; + case SnapToBeatDiv20: return 20; + case SnapToBeatDiv16: return 16; + case SnapToBeatDiv14: return 14; + case SnapToBeatDiv12: return 12; + case SnapToBeatDiv10: return 10; + case SnapToBeatDiv8: return 8; + case SnapToBeatDiv7: return 7; + case SnapToBeatDiv6: return 6; + case SnapToBeatDiv5: return 5; + case SnapToBeatDiv4: return 4; + case SnapToBeatDiv3: return 3; + case SnapToBeatDiv2: return 2; + case SnapToBeat: return 1; + case SnapToBar : return -1; + default: return 0; + } + return 0; +} + Evoral::Beats Editor::get_grid_type_as_beats (bool& success, framepos_t position) { @@ -4248,7 +4262,7 @@ Editor::new_playlists (TimeAxisView* v) begin_reversible_command (_("new playlists")); vector > playlists; _session->playlists->get (playlists); - mapover_tracks (sigc::bind (sigc::mem_fun (*this, &Editor::mapped_use_new_playlist), playlists), v, ARDOUR::Properties::select.property_id); + mapover_tracks (sigc::bind (sigc::mem_fun (*this, &Editor::mapped_use_new_playlist), playlists), v, ARDOUR::Properties::group_select.property_id); commit_reversible_command (); } @@ -4264,7 +4278,7 @@ Editor::copy_playlists (TimeAxisView* v) begin_reversible_command (_("copy playlists")); vector > playlists; _session->playlists->get (playlists); - mapover_tracks (sigc::bind (sigc::mem_fun (*this, &Editor::mapped_use_copy_playlist), playlists), v, ARDOUR::Properties::select.property_id); + mapover_tracks (sigc::bind (sigc::mem_fun (*this, &Editor::mapped_use_copy_playlist), playlists), v, ARDOUR::Properties::group_select.property_id); commit_reversible_command (); } @@ -4279,7 +4293,7 @@ Editor::clear_playlists (TimeAxisView* v) begin_reversible_command (_("clear playlists")); vector > playlists; _session->playlists->get (playlists); - mapover_tracks (sigc::mem_fun (*this, &Editor::mapped_clear_playlist), v, ARDOUR::Properties::select.property_id); + mapover_tracks (sigc::mem_fun (*this, &Editor::mapped_clear_playlist), v, ARDOUR::Properties::group_select.property_id); commit_reversible_command (); } @@ -5190,73 +5204,94 @@ Editor::resume_route_redisplay () } void -Editor::add_vcas (VCAList& vcas) +Editor::add_vcas (VCAList& vlist) { - VCATimeAxisView* vtv; - list new_views; + StripableList sl; - for (VCAList::iterator v = vcas.begin(); v != vcas.end(); ++v) { - vtv = new VCATimeAxisView (*this, _session, *_track_canvas); - vtv->set_vca (*v); - new_views.push_back (vtv); + for (VCAList::iterator v = vlist.begin(); v != vlist.end(); ++v) { + sl.push_back (boost::dynamic_pointer_cast (*v)); } - if (new_views.size() > 0) { - _routes->vcas_added (new_views); - } + add_stripables (sl); } void -Editor::add_routes (RouteList& routes) +Editor::add_routes (RouteList& rlist) { - ENSURE_GUI_THREAD (*this, &Editor::handle_new_route, routes) + StripableList sl; + + for (RouteList::iterator r = rlist.begin(); r != rlist.end(); ++r) { + sl.push_back (*r); + } - RouteTimeAxisView *rtv; - list new_views; + add_stripables (sl); +} + +void +Editor::add_stripables (StripableList& sl) +{ + list new_views; + boost::shared_ptr v; + boost::shared_ptr r; TrackViewList new_selection; bool from_scratch = (track_views.size() == 0); - for (RouteList::iterator x = routes.begin(); x != routes.end(); ++x) { - boost::shared_ptr route = (*x); + sl.sort (StripablePresentationInfoSorter()); - if (route->is_auditioner() || route->is_monitor()) { - continue; - } + for (StripableList::iterator s = sl.begin(); s != sl.end(); ++s) { - DataType dt = route->input()->default_type(); + if ((v = boost::dynamic_pointer_cast (*s)) != 0) { - if (dt == ARDOUR::DataType::AUDIO) { - rtv = new AudioTimeAxisView (*this, _session, *_track_canvas); - rtv->set_route (route); - } else if (dt == ARDOUR::DataType::MIDI) { - rtv = new MidiTimeAxisView (*this, _session, *_track_canvas); - rtv->set_route (route); - } else { - throw unknown_type(); - } + VCATimeAxisView* vtv = new VCATimeAxisView (*this, _session, *_track_canvas); + vtv->set_vca (v); + new_views.push_back (vtv); - new_views.push_back (rtv); - track_views.push_back (rtv); - new_selection.push_back (rtv); + } else if ((r = boost::dynamic_pointer_cast (*s)) != 0) { - rtv->effective_gain_display (); + if (r->is_auditioner() || r->is_monitor()) { + continue; + } - rtv->view()->RegionViewAdded.connect (sigc::mem_fun (*this, &Editor::region_view_added)); - rtv->view()->RegionViewRemoved.connect (sigc::mem_fun (*this, &Editor::region_view_removed)); + RouteTimeAxisView* rtv; + DataType dt = r->input()->default_type(); + + if (dt == ARDOUR::DataType::AUDIO) { + rtv = new AudioTimeAxisView (*this, _session, *_track_canvas); + rtv->set_route (r); + } else if (dt == ARDOUR::DataType::MIDI) { + rtv = new MidiTimeAxisView (*this, _session, *_track_canvas); + rtv->set_route (r); + } else { + throw unknown_type(); + } + + new_views.push_back (rtv); + track_views.push_back (rtv); + new_selection.push_back (rtv); + + rtv->effective_gain_display (); + + rtv->view()->RegionViewAdded.connect (sigc::mem_fun (*this, &Editor::region_view_added)); + rtv->view()->RegionViewRemoved.connect (sigc::mem_fun (*this, &Editor::region_view_removed)); + } } if (new_views.size() > 0) { - _routes->routes_added (new_views); - _summary->routes_added (new_views); + _routes->time_axis_views_added (new_views); + //_summary->routes_added (new_selection); /* XXX requires RouteTimeAxisViewList */ } - if (!from_scratch) { + /* note: !new_selection.empty() means that we got some routes rather + * than just VCAs + */ + + if (!from_scratch && !new_selection.empty()) { selection->tracks.clear(); selection->add (new_selection); begin_selection_op_history(); } - if (show_editor_mixer_when_tracks_arrive) { + if (show_editor_mixer_when_tracks_arrive && !new_selection.empty()) { show_editor_mixer (true); }