@trans|Transport/Record|<@TERTIARY@>r|engage record
@mmode|MouseMode/set-mouse-mode-timefx|t|timefx mode
@select|Editor/select-all-tracks|<@PRIMARY@>t|select all tracks
-@mmode|MouseMode/set-mouse-mode-object-range|y|link object/range tools
@edit|Editor/alternate-redo|<@PRIMARY@>y|redo
@select|Editor/select-all-between-cursors|<@PRIMARY@>u|all enclosed by edit range
@select|Editor/select-all-within-cursors|u|all present in edit range
;; MIDDLE ROW
-@aep|Region/align-regions-sync-relative|a|align sync points (relative)
+@trans|Transport/solo-selection|a|solo selection
@select|Editor/select-all-objects|<@PRIMARY@>a|select all objects
@aep|Region/align-regions-end|<@SECONDARY@>a|align end(s)
@aep|Region/align-regions-sync|<@TERTIARY@>a|align sync points
@edit|Editor/undo|<@PRIMARY@>z|undo
@edit|Editor/alternate-alternate-redo|<@PRIMARY@><@TERTIARY@>z|redo
@vis|Editor/toggle-zoom|<@TERTIARY@>z|toggle last 2 zoom states
-@mmode|MouseMode/set-mouse-mode-cut|c|cut mode
+@aep|Region/align-regions-sync-relative|x|align sync points (relative)
@edit|Editor/editor-cut|<@PRIMARY@>x|cut
+@mmode|MouseMode/set-mouse-mode-cut|c|cut mode
@edit|Editor/editor-copy|<@PRIMARY@>c|copy
@wvis|Window/toggle-big-clock|<@SECONDARY@>c|toggle big clock
@-edit|Editor/crop|<@PRIMARY@><@TERTIARY@>c|crop
@gmode|Transport/ToggleAutoPlay|5|toggle auto play
@gmode|Transport/ToggleAutoReturn|6|toggle auto return
@gmode|Transport/ToggleClick|7|toggle click (metronome)
+@mmode|MouseMode/set-mouse-mode-object-range|8|link object/range tools
@ranges|Region/set-tempo-from-region|9|set tempo (1 bar) from region(s)
@ranges|Editor/set-tempo-from-edit-range|0|set tempo (1 bar) from edit range
<menuitem action='ToggleRoll'/>
<menu action="PlayMenu">
<menuitem action='PlaySelection'/>
+ <menuitem action='solo-selection'/>
<menuitem action='PlayPreroll'/>
<menuitem action='ToggleRollMaybe'/>
<menuitem action='play-from-edit-point-and-return'/>
act = global_actions.register_action (transport_actions, X_("PlayPreroll"), _("Play w/Preroll"), sigc::mem_fun(*this, &ARDOUR_UI::transport_play_preroll));
ActionManager::session_sensitive_actions.push_back (act);
ActionManager::transport_sensitive_actions.push_back (act);
+ act = global_actions.register_action (transport_actions, X_("solo-selection"), _("Solo Selection"), sigc::bind (sigc::mem_fun(*editor, &PublicEditor::play_solo_selection), true));
+ ActionManager::session_sensitive_actions.push_back (act);
+ ActionManager::transport_sensitive_actions.push_back (act);
+
act = global_actions.register_action (transport_actions, X_("RecordPreroll"), _("Record w/Preroll"), sigc::mem_fun(*this, &ARDOUR_UI::transport_rec_preroll));
ActionManager::session_sensitive_actions.push_back (act);
_summary = new EditorSummary (this);
selection->TimeChanged.connect (sigc::mem_fun(*this, &Editor::time_selection_changed));
+ selection->TracksChanged.connect (sigc::mem_fun(*this, &Editor::track_selection_changed));
editor_regions_selection_changed_connection = selection->RegionsChanged.connect (sigc::mem_fun(*this, &Editor::region_selection_changed));
if (!ARDOUR::Profile->get_mixbus()) {
mouse_mode_hbox->pack_start (mouse_cut_button, false, false);
+ mouse_mode_hbox->pack_start (mouse_audition_button, false, false);
}
if (!ARDOUR::Profile->get_trx()) {
mouse_mode_hbox->pack_start (mouse_timefx_button, false, false);
- mouse_mode_hbox->pack_start (mouse_audition_button, false, false);
mouse_mode_hbox->pack_start (mouse_draw_button, false, false);
mouse_mode_hbox->pack_start (mouse_content_button, false, false);
}
void toggle_mute ();
void toggle_region_lock_style ();
+ void play_solo_selection( bool restart );
+
enum LayerOperation {
Raise,
RaiseToTop,
SelectionMemento* _selection_memento;
void time_selection_changed ();
+ void track_selection_changed ();
void update_time_selection_display ();
void presentation_info_changed (PBD::PropertyChange const &);
void region_selection_changed ();
/* XXX what if its a music time selection? */
if (s) {
- if (s->get_play_range() && s->transport_rolling()) {
- s->request_play_range (&_editor->selection->time, true);
- } else if (!s->config.get_external_sync()) {
- if (UIConfiguration::instance().get_follow_edits() && !s->transport_rolling()) {
- s->request_locate (_editor->get_selection().time.start());
+
+ //if Follow Edits is on, maybe try to follow the range selection ... also consider range-audition mode
+ if ( !s->config.get_external_sync() && s->transport_rolling() ) {
+ if ( s->solo_selection_active() ) {
+ _editor->play_solo_selection(true); //play the newly selected range, and move solos to match
+ } else if ( UIConfiguration::instance().get_follow_edits() && s->get_play_range() ) { //already rolling a selected range
+ s->request_play_range (&_editor->selection->time, true); //play the newly selected range
}
+ } else if ( !s->transport_rolling() && UIConfiguration::instance().get_follow_edits() ) {
+ s->request_locate (_editor->get_selection().time.start());
}
if (_editor->get_selection().time.length() != 0) {
if (ARDOUR::Profile->get_mixbus()) {
if ( m == MouseCut) m = MouseObject;
+ if ( m == MouseAudition) m = MouseRange;
}
Glib::RefPtr<Action> act = get_mouse_mode_action(m);
{
if (ARDOUR::Profile->get_mixbus()) {
if ( m == MouseCut) m = MouseObject;
+ if ( m == MouseAudition) m = MouseRange;
}
Glib::RefPtr<Action> act = get_mouse_mode_action(m);
_drags->abort ();
} else {
selection->clear ();
+
+ //if session is playing a range, cancel that
+ if (_session->get_play_range()) {
+ _session->request_cancel_play_range();
+ }
+
+ if ( _session->solo_selection_active() ) {
+ StripableList sl;
+ _session->solo_selection( sl, false );
+ }
+
}
ARDOUR_UI::instance()->reset_focus (&contents());
Editor::temporal_zoom_selection (Editing::ZoomAxis axes)
{
if (!selection) return;
+
+ if ( selection->regions.empty() && selection->time.empty() ) {
+ if (axes == Horizontal || axes == Both) {
+ temporal_zoom_step(true);
+ }
+ if (axes == Vertical || axes == Both) {
+ if ( !track_views.empty() ) {
+
+ TrackViewList tvl;
+
+ //implicit hack: by extending the top & bottom check outside the current view limits, we include the trackviews immediately above & below what is visible
+ const double top = vertical_adjustment.get_value() - 10;
+ const double btm = top + _visible_canvas_height + 10;
+
+ for (TrackViewList::iterator iter = track_views.begin(); iter != track_views.end(); ++iter) {
+ if ( (*iter)->covered_by_y_range (top, btm) ) {
+ tvl.push_back(*iter);
+ }
+ }
+
+ fit_tracks (tvl);
+ }
+ }
+ return;
+ }
//ToDo: if notes are selected, zoom to that
}
}
+StripableList
+tracklist_to_stripables( TrackViewList list )
+{
+ StripableList ret;
+
+ for (TrackSelection::iterator i = list.begin(); i != list.end(); ++i) {
+ RouteTimeAxisView* rtv = dynamic_cast<RouteTimeAxisView*> ((*i));
+
+ if (rtv && rtv->is_track()) {
+ ret.push_back( rtv->track() );
+ }
+ }
+
+ return ret;
+}
+
+void
+Editor::play_solo_selection (bool restart)
+{
+ //note: session::solo_selection takes care of invalidating the region playlist
+
+ if ( (!selection->tracks.empty()) && selection->time.length() > 0 ) { //a range is selected; solo the tracks and roll
+
+ StripableList sl = tracklist_to_stripables (selection->tracks);
+ _session->solo_selection( sl, true );
+
+ if ( restart ) {
+ samplepos_t start = selection->time.start();
+ samplepos_t end = selection->time.end_sample();
+ _session->request_bounded_roll (start, end);
+ }
+ } else if ( ! selection->tracks.empty() ) { //no range is selected, but tracks are selected; solo the tracks and roll
+ StripableList sl = tracklist_to_stripables (selection->tracks);
+ _session->solo_selection( sl, true );
+ _session->request_cancel_play_range();
+ transition_to_rolling (true);
+
+ } else if ( ! selection->regions.empty() ) { //solo any tracks with selected regions, and roll
+ StripableList sl = tracklist_to_stripables ( get_tracks_for_range_action() );
+ _session->solo_selection( sl, true );
+ _session->request_cancel_play_range();
+ transition_to_rolling (true);
+ } else {
+ _session->request_cancel_play_range();
+ transition_to_rolling (true); //no selection. just roll.
+ }
+}
+
void
Editor::toggle_solo ()
{
}
}
+void
+Editor::track_selection_changed ()
+{
+ if ( _session->solo_selection_active() )
+ play_solo_selection(false);
+}
+
void
Editor::time_selection_changed ()
{
}
}
+ if ( _session->solo_selection_active() )
+ play_solo_selection(false);
}
void
virtual void set_selection (std::list<Selectable*>, Selection::Operation) = 0;
virtual bool extend_selection_to_track (TimeAxisView&) = 0;
+ virtual void play_solo_selection(bool restart) = 0;
virtual void play_selection () = 0;
virtual void play_with_preroll () = 0;
virtual void rec_with_preroll () = 0;
~RegionView ();
+ virtual void set_selected (bool yn) {
+ _region->set_selected_for_solo(yn);
+ TimeAxisViewItem::set_selected(yn);
+ }
+
virtual void init (bool wait_for_data);
boost::shared_ptr<ARDOUR::Region> region() const { return _region; }
tracks.push_back (tav);
}
}
+
+ TracksChanged();
}
// Selection& operator= (const Selection& other);
+ sigc::signal<void> TracksChanged;
sigc::signal<void> RegionsChanged;
sigc::signal<void> TimeChanged;
sigc::signal<void> LinesChanged;