From 1559829e2467abe7aa2022f16794e47533d9b473 Mon Sep 17 00:00:00 2001 From: David Robillard Date: Thu, 17 Jun 2021 11:02:08 -0400 Subject: [PATCH] Factor out SessionController from BasicUI Towards sharing this code with ARDOUR_UI. --- libs/surfaces/cc121/cc121.cc | 18 +- libs/surfaces/contourdesign/contourdesign.cc | 14 +- libs/surfaces/control_protocol/basic_ui.cc | 630 +--------------- .../control_protocol/basic_ui.h | 74 +- .../control_protocol/session_controller.h | 141 ++++ .../control_protocol/session_controller.cc | 685 ++++++++++++++++++ libs/surfaces/control_protocol/wscript | 1 + libs/surfaces/faderport/faderport.cc | 28 +- libs/surfaces/faderport8/actions.cc | 28 +- libs/surfaces/faderport8/callbacks.cc | 6 +- libs/surfaces/generic_midi/midifunction.cc | 18 +- .../surfaces/launch_control_xl/controllers.cc | 2 +- libs/surfaces/mackie/jog_wheel.cc | 4 +- libs/surfaces/mackie/mcp_buttons.cc | 36 +- libs/surfaces/mackie/strip.cc | 2 +- libs/surfaces/maschine2/callbacks.cc | 14 +- libs/surfaces/osc/osc.cc | 20 +- libs/surfaces/osc/osc.h | 98 ++- libs/surfaces/push2/buttons.cc | 30 +- libs/surfaces/push2/push2.cc | 2 +- libs/surfaces/us2400/mcp_buttons.cc | 32 +- libs/surfaces/us2400/strip.cc | 2 +- libs/surfaces/websockets/transport.cc | 6 +- libs/surfaces/wiimote/wiimote.cc | 8 +- 24 files changed, 1050 insertions(+), 849 deletions(-) create mode 100644 libs/surfaces/control_protocol/control_protocol/session_controller.h create mode 100644 libs/surfaces/control_protocol/session_controller.cc diff --git a/libs/surfaces/cc121/cc121.cc b/libs/surfaces/cc121/cc121.cc index 9b47cb62d4..a837e5d1b3 100644 --- a/libs/surfaces/cc121/cc121.cc +++ b/libs/surfaces/cc121/cc121.cc @@ -160,15 +160,15 @@ CC121::CC121 (Session& s) get_button (EButton).set_action (boost::bind (&CC121::touch, this), true); get_button (OpenVST).set_action (boost::bind (&CC121::off, this), true); - get_button (Play).set_action (boost::bind (&BasicUI::transport_play, this, true), true); - get_button (ToStart).set_action (boost::bind (&BasicUI::prev_marker, this), true); - get_button (ToEnd).set_action (boost::bind (&BasicUI::next_marker, this), true); - get_button (RecEnable).set_action (boost::bind (&BasicUI::rec_enable_toggle, this), true); - get_button (Stop).set_action (boost::bind (&BasicUI::transport_stop, this), true); - get_button (Ffwd).set_action (boost::bind (&BasicUI::ffwd, this), true); + get_button (Play).set_action (boost::bind (&SessionController::transport_play, _controller, true), true); + get_button (ToStart).set_action (boost::bind (&SessionController::prev_marker, _controller), true); + get_button (ToEnd).set_action (boost::bind (&SessionController::next_marker, _controller), true); + get_button (RecEnable).set_action (boost::bind (&SessionController::rec_enable_toggle, _controller), true); + get_button (Stop).set_action (boost::bind (&SessionController::transport_stop, _controller), true); + get_button (Ffwd).set_action (boost::bind (&SessionController::ffwd, _controller), true); - get_button (Rewind).set_action (boost::bind (&BasicUI::rewind, this), true); - get_button (Loop).set_action (boost::bind (&BasicUI::loop_toggle, this), true); + get_button (Rewind).set_action (boost::bind (&SessionController::rewind, _controller), true); + get_button (Loop).set_action (boost::bind (&SessionController::loop_toggle, _controller), true); get_button (Jog).set_action (boost::bind (&CC121::jog, this), true); get_button (Mute).set_action (boost::bind (&CC121::mute, this), true); @@ -669,7 +669,7 @@ CC121::map_transport_state () { get_button (Loop).set_led_state (_output_port, _session->get_play_loop()); - float ts = get_transport_speed(); + float ts = _controller.get_transport_speed(); if (ts == 0) { stop_blinking (Play); diff --git a/libs/surfaces/contourdesign/contourdesign.cc b/libs/surfaces/contourdesign/contourdesign.cc index 7b56238337..9b600ec294 100644 --- a/libs/surfaces/contourdesign/contourdesign.cc +++ b/libs/surfaces/contourdesign/contourdesign.cc @@ -574,9 +574,9 @@ ContourDesignControlProtocol::jump_forward (JumpDistance dist) { LocateTransportDisposition kr = _keep_rolling ? RollIfAppropriate : MustStop; switch (dist.unit) { - case SECONDS: jump_by_seconds (dist.value, kr); break; - case BEATS: jump_by_beats (dist.value, kr); break; - case BARS: jump_by_bars (dist.value, kr); break; + case SECONDS: _controller.jump_by_seconds (dist.value, kr); break; + case BEATS: _controller.jump_by_beats (dist.value, kr); break; + case BARS: _controller.jump_by_bars (dist.value, kr); break; default: break; } } @@ -607,17 +607,17 @@ ContourDesignControlProtocol::shuttle_event (int position) if (position != 0) { if (_shuttle_was_zero) { - _was_rolling_before_shuttle = transport_rolling (); + _was_rolling_before_shuttle = _controller.transport_rolling (); } const vector& spds = _shuttle_speeds; const double speed = position > 0 ? spds[position-1] : -spds[-position-1]; - set_transport_speed (speed); + _controller.set_transport_speed (speed); _shuttle_was_zero = false; } else { if (_keep_rolling && _was_rolling_before_shuttle) { - set_transport_speed (1.0); + _controller.set_transport_speed (1.0); } else { - transport_stop (); + _controller.transport_stop (); } _shuttle_was_zero = true; } diff --git a/libs/surfaces/control_protocol/basic_ui.cc b/libs/surfaces/control_protocol/basic_ui.cc index 7cdd3a08ca..f8a4e2709c 100644 --- a/libs/surfaces/control_protocol/basic_ui.cc +++ b/libs/surfaces/control_protocol/basic_ui.cc @@ -42,6 +42,7 @@ PBD::Signal2 BasicUI::AccessAction; BasicUI::BasicUI (Session& s) : _session (&s) + , _controller (&s) { } @@ -69,226 +70,6 @@ BasicUI::access_action ( std::string action_path ) AccessAction( group, item ); } -void -BasicUI::loop_toggle () -{ - if (!_session) { - return; - } - - Location * looploc = _session->locations()->auto_loop_location(); - - if (!looploc) { - return; - } - - if (_session->get_play_loop()) { - - /* looping enabled, our job is to disable it */ - - _session->request_play_loop (false); - - } else { - - /* looping not enabled, our job is to enable it. - - loop-is-NOT-mode: this action always starts the transport rolling. - loop-IS-mode: this action simply sets the loop play mechanism, but - does not start transport. - */ - if (Config->get_loop_is_mode()) { - _session->request_play_loop (true, false); - } else { - _session->request_play_loop (true, true); - } - } - - //show the loop markers - looploc->set_hidden (false, this); -} - -void -BasicUI::loop_location (samplepos_t start, samplepos_t end) -{ - Location* tll; - if ((tll = _session->locations()->auto_loop_location()) == 0) { - Location* loc = new Location (*_session, start, end, _("Loop"), Location::IsAutoLoop); - _session->locations()->add (loc, true); - _session->set_auto_loop_location (loc); - } else { - tll->set_hidden (false, this); - tll->set (start, end); - } -} - -void -BasicUI::goto_start (bool and_roll) -{ - _session->goto_start (and_roll); -} - -void -BasicUI::goto_zero () -{ - _session->request_locate (0); -} - -void -BasicUI::goto_end () -{ - _session->goto_end (); -} - -void -BasicUI::add_marker (const std::string& markername) -{ - samplepos_t where = _session->audible_sample(); - Location *location = new Location (*_session, where, where, markername, Location::IsMark); - _session->begin_reversible_command (_("add marker")); - XMLNode &before = _session->locations()->get_state(); - _session->locations()->add (location, true); - XMLNode &after = _session->locations()->get_state(); - _session->add_command (new MementoCommand(*(_session->locations()), &before, &after)); - _session->commit_reversible_command (); -} - -void -BasicUI::remove_marker_at_playhead () -{ - if (_session) { - //set up for undo - XMLNode &before = _session->locations()->get_state(); - bool removed = false; - - //find location(s) at this time - Locations::LocationList locs; - _session->locations()->find_all_between (_session->audible_sample(), _session->audible_sample()+1, locs, Location::Flags(0)); - for (Locations::LocationList::iterator i = locs.begin(); i != locs.end(); ++i) { - if ((*i)->is_mark()) { - _session->locations()->remove (*i); - removed = true; - } - } - - //store undo - if (removed) { - _session->begin_reversible_command (_("remove marker")); - XMLNode &after = _session->locations()->get_state(); - _session->add_command(new MementoCommand(*(_session->locations()), &before, &after)); - _session->commit_reversible_command (); - } - } -} - -void -BasicUI::button_varispeed (bool fwd) -{ - // incrementally increase speed by semitones - // (keypress auto-repeat is 100ms) - const float maxspeed = Config->get_shuttle_max_speed(); - float semitone_ratio = exp2f (1.0f/12.0f); - const float octave_down = pow (1.0/semitone_ratio, 12.0); - float transport_speed = get_transport_speed (); - float speed; - - if (Config->get_rewind_ffwd_like_tape_decks()) { - - if (fwd) { - if (transport_speed <= 0) { - _session->request_transport_speed (1.0, false); - _session->request_roll (TRS_UI); - return; - } - } else { - if (transport_speed >= 0) { - _session->request_transport_speed (-1.0, false); - _session->request_roll (TRS_UI); - return; - } - } - - - } else { - - if (fabs (transport_speed) <= 0.1) { - - /* close to zero, maybe flip direction */ - - if (fwd) { - if (transport_speed <= 0) { - _session->request_transport_speed (1.0, false); - _session->request_roll (TRS_UI); - } - } else { - if (transport_speed >= 0) { - _session->request_transport_speed (-1.0, false); - _session->request_roll (TRS_UI); - } - } - - /* either we've just started, or we're moving as slowly as we - * ever should - */ - - return; - } - - if (fwd) { - if (transport_speed < 0.f) { - if (fabs (transport_speed) < octave_down) { - /* we need to move the speed back towards zero */ - semitone_ratio = powf (1.f / semitone_ratio, 4.f); - } else { - semitone_ratio = 1.f / semitone_ratio; - } - } else { - if (fabs (transport_speed) < octave_down) { - /* moving very slowly, use 4 semitone steps */ - semitone_ratio = powf (semitone_ratio, 4.f); - } - } - } else { - if (transport_speed > 0.f) { - /* we need to move the speed back towards zero */ - - if (transport_speed < octave_down) { - semitone_ratio = powf (1.f / semitone_ratio, 4.f); - } else { - semitone_ratio = 1.f / semitone_ratio; - } - } else { - if (fabs (transport_speed) < octave_down) { - /* moving very slowly, use 4 semitone steps */ - semitone_ratio = powf (semitone_ratio, 4.f); - } - } - } - } - - speed = semitone_ratio * transport_speed; - speed = std::max (-maxspeed, std::min (maxspeed, speed)); - _session->request_transport_speed (speed, false); - _session->request_roll (TRS_UI); -} - -void -BasicUI::rewind () -{ - button_varispeed (false); -} - -void -BasicUI::ffwd () -{ - button_varispeed (true); -} - -void -BasicUI::transport_stop () -{ - _session->request_stop (); -} - bool BasicUI::stop_button_onoff () const { @@ -298,19 +79,19 @@ BasicUI::stop_button_onoff () const bool BasicUI::play_button_onoff () const { - return get_transport_speed() == 1.0; + return _controller.get_transport_speed() == 1.0; } bool BasicUI::ffwd_button_onoff () const { - return get_transport_speed() > 1.0; + return _controller.get_transport_speed() > 1.0; } bool BasicUI::rewind_button_onoff () const { - return get_transport_speed() < 0.0; + return _controller.get_transport_speed() < 0.0; } bool @@ -319,129 +100,6 @@ BasicUI::loop_button_onoff () const return _session->get_play_loop(); } -void -BasicUI::transport_play (bool from_last_start) -{ - /* ::toggle_roll() is smarter and preferred */ - - if (!_session) { - return; - } - - if (_session->is_auditioning()) { - return; - } - - bool rolling = transport_rolling(); - - if (_session->get_play_loop()) { - - /* If loop playback is not a mode, then we should cancel - it when this action is requested. If it is a mode - we just leave it in place. - */ - - if (!Config->get_loop_is_mode()) { - /* XXX it is not possible to just leave seamless loop and keep - playing at present (nov 4th 2009) - */ - if (rolling) { - /* stop loop playback but keep rolling */ - _session->request_play_loop (false, false); - } - } - - } else if (_session->get_play_range () ) { - /* stop playing a range if we currently are */ - _session->request_play_range (0, true); - } - - if (rolling) { - _session->request_transport_speed (1.0, false, TRS_UI); - } else { - _session->request_roll (); - } -} - -void -BasicUI::rec_enable_toggle () -{ - switch (_session->record_status()) { - case (RecordState)Disabled: - if (_session->ntracks() == 0) { - // string txt = _("Please create 1 or more track\nbefore trying to record.\nCheck the Session menu."); - // MessageDialog msg (*editor, txt); - // msg.run (); - return; - } - _session->maybe_enable_record (); - break; - case (RecordState)Recording: - case (RecordState)Enabled: - _session->disable_record (false, true); - } -} - -void -BasicUI::all_tracks_rec_in () -{ - _session->set_all_tracks_record_enabled (true); -} - -void -BasicUI::all_tracks_rec_out () -{ - _session->set_all_tracks_record_enabled (false); -} - -void -BasicUI::save_state () -{ - _session->save_state (""); -} - -void -BasicUI::prev_marker () -{ - samplepos_t pos = _session->locations()->first_mark_before (_session->transport_sample()); - - if (pos >= 0) { - _session->request_locate (pos); - } else { - _session->goto_start (); - } -} - -void -BasicUI::next_marker () -{ - samplepos_t pos = _session->locations()->first_mark_after (_session->transport_sample()); - - if (pos >= 0) { - _session->request_locate (pos); - } else { - _session->goto_end(); - } -} - -void -BasicUI::set_transport_speed (double speed) -{ - _session->request_transport_speed (speed); -} - -double -BasicUI::get_transport_speed () const -{ - return _session->actual_speed (); -} - -double -BasicUI::transport_rolling () const -{ - return !_session->transport_stopped_or_stopping (); -} - void BasicUI::undo () { @@ -454,227 +112,6 @@ BasicUI::redo () access_action ("Editor/redo"); } -void -BasicUI::toggle_all_rec_enables () -{ - if (_session->get_record_enabled()) { - // _session->record_disenable_all (); - } else { - // _session->record_enable_all (); - } -} - -void -BasicUI::toggle_punch_in () -{ - _session->config.set_punch_in (!_session->config.get_punch_in()); -} - -void -BasicUI::toggle_punch_out () -{ - _session->config.set_punch_out (!_session->config.get_punch_out()); -} - -bool -BasicUI::get_record_enabled () -{ - return _session->get_record_enabled(); -} - -void -BasicUI::set_record_enable (bool yn) -{ - if (yn) { - _session->maybe_enable_record (); - } else { - _session->disable_record (false, true); - } -} - -samplepos_t -BasicUI::transport_sample () -{ - return _session->transport_sample(); -} - -void -BasicUI::locate (samplepos_t where, LocateTransportDisposition ltd) -{ - _session->request_locate (where, ltd); -} - -void -BasicUI::locate (samplepos_t where, bool roll) -{ - _session->request_locate (where, roll ? MustRoll : RollIfAppropriate); -} - -void -BasicUI::jump_by_seconds (double secs, LocateTransportDisposition ltd) -{ - samplepos_t current = _session->transport_sample(); - double s = (double) current / (double) _session->nominal_sample_rate(); - - s+= secs; - if (s < 0) { - s = 0; - } - s = s * _session->nominal_sample_rate(); - - _session->request_locate (floor(s), ltd); -} - -void -BasicUI::jump_by_bars (double bars, LocateTransportDisposition ltd) -{ - TempoMap& tmap (_session->tempo_map()); - Timecode::BBT_Time bbt (tmap.bbt_at_sample (_session->transport_sample())); - - bars += bbt.bars; - if (bars < 0) { - bars = 0; - } - - AnyTime any; - any.type = AnyTime::BBT; - any.bbt.bars = bars; - - _session->request_locate (_session->convert_to_samples (any), ltd); -} - -void -BasicUI::jump_by_beats (double beats, LocateTransportDisposition ltd) -{ - TempoMap& tmap (_session->tempo_map ()); - double qn_goal = tmap.quarter_note_at_sample (_session->transport_sample ()) + beats; - if (qn_goal < 0.0) { - qn_goal = 0.0; - } - _session->request_locate (tmap.sample_at_quarter_note (qn_goal), ltd); -} - -void -BasicUI::toggle_monitor_mute () -{ - if (_session->monitor_out()) { - boost::shared_ptr mon = _session->monitor_out()->monitor_control(); - if (mon->cut_all ()) { - mon->set_cut_all (false); - } else { - mon->set_cut_all (true); - } - } -} - -void -BasicUI::toggle_monitor_dim () -{ - if (_session->monitor_out()) { - boost::shared_ptr mon = _session->monitor_out()->monitor_control(); - if (mon->dim_all ()) { - mon->set_dim_all (false); - } else { - mon->set_dim_all (true); - } - } -} - -void -BasicUI::toggle_monitor_mono () -{ - if (_session->monitor_out()) { - boost::shared_ptr mon = _session->monitor_out()->monitor_control(); - if (mon->mono()) { - mon->set_mono (false); - } else { - mon->set_mono (true); - } - } -} - -void -BasicUI::midi_panic () -{ - _session->midi_panic (); -} - -void -BasicUI::toggle_click () -{ - bool state = !Config->get_clicking(); - Config->set_clicking (state); -} - -void -BasicUI::toggle_roll (bool roll_out_of_bounded_mode) -{ - /* TO BE KEPT IN SYNC WITH ARDOUR_UI::toggle_roll() */ - - if (!_session) { - return; - } - - if (_session->is_auditioning()) { - _session->cancel_audition (); - return; - } - - if (_session->config.get_external_sync()) { - switch (TransportMasterManager::instance().current()->type()) { - case Engine: - break; - default: - /* transport controlled by the master */ - return; - } - } - - bool rolling = transport_rolling(); - - if (rolling) { - - if (roll_out_of_bounded_mode) { - /* drop out of loop/range playback but leave transport rolling */ - - if (_session->get_play_loop()) { - - if (_session->actively_recording()) { - /* actually stop transport because - otherwise the captured data will make - no sense. - */ - _session->request_play_loop (false, true); - - } else { - _session->request_play_loop (false, false); - } - - } else if (_session->get_play_range ()) { - - _session->request_cancel_play_range (); - } - - } else { - _session->request_stop (true, true); - } - - } else { /* not rolling */ - - if (_session->get_play_loop() && Config->get_loop_is_mode()) { - _session->request_locate (_session->locations()->auto_loop_location()->start(), MustRoll); - } else { - _session->request_roll (TRS_UI); - } - } -} - -void -BasicUI::stop_forget () -{ - _session->request_stop (true, true); -} - void BasicUI::mark_in () { access_action("Common/start-range-from-playhead"); } void BasicUI::mark_out () { access_action("Common/finish-range-from-playhead"); } @@ -708,62 +145,3 @@ void BasicUI::scroll_up_1_track() { access_action("Editor/step-tracks-up"); } void BasicUI::scroll_dn_1_track() { access_action("Editor/step-tracks-down"); } void BasicUI::scroll_up_1_page() { access_action("Editor/scroll-tracks-up"); } void BasicUI::scroll_dn_1_page() { access_action("Editor/scroll-tracks-down"); } - - -bool -BasicUI::locating () -{ - return _session->locate_pending(); -} - -bool -BasicUI::locked () -{ - return _session->transport_locked (); -} - -void -BasicUI::timecode_time (samplepos_t where, Timecode::Time& timecode) -{ - _session->timecode_time (where, *((Timecode::Time *) &timecode)); -} - -void -BasicUI::cancel_all_solo () -{ - if (_session) { - _session->cancel_all_solo (); - } -} - -struct SortLocationsByPosition { - bool operator() (Location* a, Location* b) { - return a->start() < b->start(); - } -}; - -void -BasicUI::goto_nth_marker (int n) -{ - if (!_session) { - return; - } - - const Locations::LocationList& l (_session->locations()->list()); - Locations::LocationList ordered; - ordered = l; - - SortLocationsByPosition cmp; - ordered.sort (cmp); - - for (Locations::LocationList::iterator i = ordered.begin(); n >= 0 && i != ordered.end(); ++i) { - if ((*i)->is_mark() && !(*i)->is_hidden() && !(*i)->is_session_range()) { - if (n == 0) { - _session->request_locate ((*i)->start()); - break; - } - --n; - } - } -} - diff --git a/libs/surfaces/control_protocol/control_protocol/basic_ui.h b/libs/surfaces/control_protocol/control_protocol/basic_ui.h index 6070817d5d..ff366fef42 100644 --- a/libs/surfaces/control_protocol/control_protocol/basic_ui.h +++ b/libs/surfaces/control_protocol/control_protocol/basic_ui.h @@ -25,6 +25,7 @@ #include "ardour/presentation_info.h" #include "ardour/types.h" +#include "control_protocol/session_controller.h" #include "control_protocol/visibility.h" #include "pbd/signals.h" #include "temporal/time.h" @@ -41,75 +42,37 @@ class LIBCONTROLCP_API BasicUI { BasicUI (Session&); virtual ~BasicUI (); - void add_marker (const std::string& = std::string()); - void remove_marker_at_playhead (); - void register_thread (std::string name); - /* transport control */ + /* Access to GUI actions */ + + void access_action (std::string action_path); - void loop_toggle (); - void loop_location (samplepos_t start, samplepos_t end); - void access_action ( std::string action_path ); static PBD::Signal2 AccessAction; - void goto_zero (); - void goto_start (bool and_roll = false); - void goto_end (); - void button_varispeed (bool fwd); - void rewind (); - void ffwd (); - void transport_stop (); - void transport_play (bool jump_back = false); - void set_transport_speed (double speed); - double get_transport_speed () const; - double transport_rolling () const; + /* Undo/Redo */ - void jump_by_seconds (double sec, LocateTransportDisposition ltd = RollIfAppropriate); - void jump_by_bars (double bars, LocateTransportDisposition ltd = RollIfAppropriate); - void jump_by_beats (double beats, LocateTransportDisposition ltd = RollIfAppropriate); - - samplepos_t transport_sample (); - void locate (samplepos_t sample, LocateTransportDisposition ltd); - void locate (samplepos_t sample, bool); - bool locating (); - bool locked (); - - void save_state (); - void prev_marker (); - void next_marker (); void undo (); void redo (); - void toggle_punch_in (); - void toggle_punch_out (); + + /* Convenience methods that fire actions */ void mark_in(); void mark_out(); - void toggle_click(); - void midi_panic(); - - void toggle_monitor_mute(); - void toggle_monitor_dim(); - void toggle_monitor_mono(); - - void cancel_all_solo (); - void quick_snapshot_stay (); void quick_snapshot_switch (); - void toggle_roll(bool roll_out_of_bounded_mode=true); //this provides the same operation as the "spacebar", it's a lot smarter than "play". - - void stop_forget(); - void set_punch_range(); void set_loop_range(); void set_session_range(); - void set_record_enable (bool yn); - bool get_record_enabled (); + /* Editor Visibility + + We need to explicitly bake in the "arguments" here, because GUI actions + don't have arguments. + */ - //editor visibility stuff (why do we have to make explicit numbers here? because "gui actions" don't accept args void fit_1_track(); void fit_2_tracks(); void fit_4_tracks(); @@ -133,15 +96,7 @@ class LIBCONTROLCP_API BasicUI { void scroll_up_1_page(); void scroll_dn_1_page(); - void rec_enable_toggle (); - void toggle_all_rec_enables (); - - void all_tracks_rec_in (); - void all_tracks_rec_out (); - - void goto_nth_marker (int n); - - void timecode_time (samplepos_t where, Timecode::Time&); + /* Button state */ bool stop_button_onoff() const; bool play_button_onoff() const; @@ -149,8 +104,11 @@ class LIBCONTROLCP_API BasicUI { bool rewind_button_onoff() const; bool loop_button_onoff() const; + SessionController& controller() { return _controller; } + protected: Session* _session; + SessionController _controller; }; } // namespace ARDOUR diff --git a/libs/surfaces/control_protocol/control_protocol/session_controller.h b/libs/surfaces/control_protocol/control_protocol/session_controller.h new file mode 100644 index 0000000000..da05ad7249 --- /dev/null +++ b/libs/surfaces/control_protocol/control_protocol/session_controller.h @@ -0,0 +1,141 @@ +/* + * Copyright (C) 2006-2021 David Robillard + * Copyright (C) 2007-2017 Paul Davis + * Copyright (C) 2010 Carl Hetherington + * Copyright (C) 2015 Robin Gareus + * Copyright (C) 2016 Ben Loftis + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#ifndef __ardour_session_controller_h__ +#define __ardour_session_controller_h__ + +#include "ardour/types.h" +#include "control_protocol/visibility.h" +#include "temporal/time.h" + +#include +#include + +namespace ARDOUR { + +class Session; + +/** A controller for a session used by UIs and control surfaces. + * + * This implements operations that manipulate a session which are common to any + * kind of UI. Application logic that isn't specific to any particular UI + * should go here and be reused, so UIs do things consistently and correctly. + * + * This only interacts with Session (and the objects it contains) directly, not + * with any UI facilities like actions or event loops. + */ +class LIBCONTROLCP_API SessionController +{ +public: + SessionController (Session* s) + : _session (s) + {} + + /* Transport Control */ + + void loop_toggle (); + void loop_location (samplepos_t start, samplepos_t end); + + void button_varispeed (bool fwd); + void rewind (); + void ffwd (); + void transport_stop (); + void transport_play (bool jump_back = false); + void set_transport_speed (double speed); + + void toggle_roll (bool roll_out_of_bounded_mode = true); + void stop_forget (); + + double get_transport_speed () const; + bool transport_rolling () const; + samplepos_t transport_sample () const; + + /* Markers */ + + void add_marker (const std::string& = std::string ()); + void remove_marker_at_playhead (); + + /* Locating */ + + void goto_zero (); + void goto_start (bool and_roll = false); + void goto_end (); + void goto_nth_marker (int n); + + void jump_by_seconds (double sec, + LocateTransportDisposition ltd = RollIfAppropriate); + + void jump_by_bars (double bars, + LocateTransportDisposition ltd = RollIfAppropriate); + + void jump_by_beats (double beats, + LocateTransportDisposition ltd = RollIfAppropriate); + + void locate (samplepos_t sample, LocateTransportDisposition ltd); + void locate (samplepos_t sample, bool); + + void prev_marker (); + void next_marker (); + + bool locating () const; + bool locked () const; + + /* State */ + + void save_state (); + + /* Monitoring */ + + void toggle_click (); + void midi_panic (); + + void toggle_monitor_mute (); + void toggle_monitor_dim (); + void toggle_monitor_mono (); + + void cancel_all_solo (); + + /* Recording */ + + void toggle_punch_in (); + void toggle_punch_out (); + + void set_record_enable (bool yn); + void rec_enable_toggle (); + void toggle_all_rec_enables (); + + void all_tracks_rec_in (); + void all_tracks_rec_out (); + + bool get_record_enabled () const; + + /* Time */ + + void timecode_time (samplepos_t where, Timecode::Time&); + +private: + Session* _session; +}; + +} // namespace ARDOUR + +#endif /* __ardour_session_controller_h__ */ diff --git a/libs/surfaces/control_protocol/session_controller.cc b/libs/surfaces/control_protocol/session_controller.cc new file mode 100644 index 0000000000..55949b90cd --- /dev/null +++ b/libs/surfaces/control_protocol/session_controller.cc @@ -0,0 +1,685 @@ +/* + * Copyright (C) 2006-2021 David Robillard + * Copyright (C) 2006-2018 Paul Davis + * Copyright (C) 2009-2010 Carl Hetherington + * Copyright (C) 2015 Robin Gareus + * Copyright (C) 2016-2017 Ben Loftis + * Copyright (C) 2017-2019 Johannes Mueller + * Copyright (C) 2017 Len Ovens + * Copyright (C) 2017 Tim Mayberry + * + * This program is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 2 of the License, or + * (at your option) any later version. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License along + * with this program; if not, write to the Free Software Foundation, Inc., + * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA. + */ + +#include "control_protocol/session_controller.h" + +#include "ardour/location.h" +#include "ardour/session.h" +#include "ardour/tempo.h" +#include "ardour/transport_master_manager.h" +#include "ardour/utils.h" +#include "pbd/i18n.h" +#include "pbd/memento_command.h" + +using namespace ARDOUR; + +/* Transport Control */ + +void +SessionController::loop_toggle () +{ + if (!_session) { + return; + } + + Location* looploc = _session->locations ()->auto_loop_location (); + + if (!looploc) { + return; + } + + if (_session->get_play_loop ()) { + /* looping enabled, our job is to disable it */ + + _session->request_play_loop (false); + + } else { + /* looping not enabled, our job is to enable it. + + loop-is-NOT-mode: this action always starts the transport rolling. + loop-IS-mode: this action simply sets the loop play mechanism, + but does not start transport. + */ + if (Config->get_loop_is_mode ()) { + _session->request_play_loop (true, false); + } else { + _session->request_play_loop (true, true); + } + } + + // show the loop markers + looploc->set_hidden (false, this); +} + +void +SessionController::loop_location (samplepos_t start, samplepos_t end) +{ + Location* const tll = _session->locations ()->auto_loop_location (); + if (!tll) { + Location* loc = new Location ( + *_session, start, end, _ ("Loop"), Location::IsAutoLoop); + + _session->locations ()->add (loc, true); + _session->set_auto_loop_location (loc); + } else { + tll->set_hidden (false, this); + tll->set (start, end); + } +} + +void +SessionController::button_varispeed (bool fwd) +{ + // incrementally increase speed by semitones + // (keypress auto-repeat is 100ms) + const float maxspeed = Config->get_shuttle_max_speed (); + float semitone_ratio = exp2f (1.0f / 12.0f); + const float octave_down = pow (1.0 / semitone_ratio, 12.0); + float transport_speed = get_transport_speed (); + float speed; + + if (Config->get_rewind_ffwd_like_tape_decks ()) { + if (fwd) { + if (transport_speed <= 0) { + _session->request_transport_speed (1.0, false); + _session->request_roll (TRS_UI); + return; + } + } else { + if (transport_speed >= 0) { + _session->request_transport_speed (-1.0, false); + _session->request_roll (TRS_UI); + return; + } + } + + } else { + if (fabs (transport_speed) <= 0.1) { + /* close to zero, maybe flip direction */ + + if (fwd) { + if (transport_speed <= 0) { + _session->request_transport_speed (1.0, false); + _session->request_roll (TRS_UI); + } + } else { + if (transport_speed >= 0) { + _session->request_transport_speed (-1.0, false); + _session->request_roll (TRS_UI); + } + } + + /* either we've just started, or we're moving as slowly as we + * ever should + */ + + return; + } + + if (fwd) { + if (transport_speed < 0.f) { + if (fabs (transport_speed) < octave_down) { + /* we need to move the speed back towards zero */ + semitone_ratio = powf (1.f / semitone_ratio, 4.f); + } else { + semitone_ratio = 1.f / semitone_ratio; + } + } else { + if (fabs (transport_speed) < octave_down) { + /* moving very slowly, use 4 semitone steps */ + semitone_ratio = powf (semitone_ratio, 4.f); + } + } + } else { + if (transport_speed > 0.f) { + /* we need to move the speed back towards zero */ + + if (transport_speed < octave_down) { + semitone_ratio = powf (1.f / semitone_ratio, 4.f); + } else { + semitone_ratio = 1.f / semitone_ratio; + } + } else { + if (fabs (transport_speed) < octave_down) { + /* moving very slowly, use 4 semitone steps */ + semitone_ratio = powf (semitone_ratio, 4.f); + } + } + } + } + + speed = semitone_ratio * transport_speed; + speed = std::max (-maxspeed, std::min (maxspeed, speed)); + _session->request_transport_speed (speed, false); + _session->request_roll (TRS_UI); +} + +void +SessionController::rewind () +{ + button_varispeed (false); +} + +void +SessionController::ffwd () +{ + button_varispeed (true); +} + +void +SessionController::transport_stop () +{ + _session->request_stop (); +} + +void +SessionController::transport_play (bool from_last_start) +{ + /* ::toggle_roll() is smarter and preferred */ + + if (!_session) { + return; + } + + if (_session->is_auditioning ()) { + return; + } + + bool rolling = transport_rolling (); + + if (_session->get_play_loop ()) { + /* If loop playback is not a mode, then we should cancel + it when this action is requested. If it is a mode + we just leave it in place. + */ + + if (!Config->get_loop_is_mode ()) { + /* XXX it is not possible to just leave seamless loop and keep + playing at present (nov 4th 2009) + */ + if (rolling) { + /* stop loop playback but keep rolling */ + _session->request_play_loop (false, false); + } + } + + } else if (_session->get_play_range ()) { + /* stop playing a range if we currently are */ + _session->request_play_range (0, true); + } + + if (rolling) { + _session->request_transport_speed (1.0, false, TRS_UI); + } else { + _session->request_roll (); + } +} + +void +SessionController::set_transport_speed (double speed) +{ + _session->request_transport_speed (speed); +} + +void +SessionController::toggle_roll (bool roll_out_of_bounded_mode) +{ + /* TO BE KEPT IN SYNC WITH ARDOUR_UI::toggle_roll() */ + + if (!_session) { + return; + } + + if (_session->is_auditioning ()) { + _session->cancel_audition (); + return; + } + + if (_session->config.get_external_sync ()) { + switch (TransportMasterManager::instance ().current ()->type ()) { + case Engine: + break; + default: + /* transport controlled by the master */ + return; + } + } + + bool rolling = transport_rolling (); + + if (rolling) { + if (roll_out_of_bounded_mode) { + /* drop out of loop/range playback but leave transport rolling */ + + if (_session->get_play_loop ()) { + if (_session->actively_recording ()) { + /* actually stop transport because + otherwise the captured data will make + no sense. + */ + _session->request_play_loop (false, true); + + } else { + _session->request_play_loop (false, false); + } + + } else if (_session->get_play_range ()) { + _session->request_cancel_play_range (); + } + + } else { + _session->request_stop (true, true); + } + + } else { /* not rolling */ + + if (_session->get_play_loop () && Config->get_loop_is_mode ()) { + _session->request_locate ( + _session->locations ()->auto_loop_location ()->start (), + MustRoll); + } else { + _session->request_roll (TRS_UI); + } + } +} + +void +SessionController::stop_forget () +{ + _session->request_stop (true, true); +} + +double +SessionController::get_transport_speed () const +{ + return _session->actual_speed (); +} + +bool +SessionController::transport_rolling () const +{ + return !_session->transport_stopped_or_stopping (); +} + +samplepos_t +SessionController::transport_sample () const +{ + return _session->transport_sample (); +} + +/* Markers */ + +void +SessionController::add_marker (const std::string& markername) +{ + const samplepos_t where = _session->audible_sample (); + + Location* location = + new Location (*_session, where, where, markername, Location::IsMark); + + _session->begin_reversible_command (_ ("add marker")); + + XMLNode& before = _session->locations ()->get_state (); + _session->locations ()->add (location, true); + XMLNode& after = _session->locations ()->get_state (); + + _session->add_command (new MementoCommand ( + *(_session->locations ()), &before, &after)); + + _session->commit_reversible_command (); +} + +void +SessionController::remove_marker_at_playhead () +{ + if (_session) { + // set up for undo + XMLNode& before = _session->locations ()->get_state (); + bool removed = false; + + // find location(s) at this time + Locations::LocationList locs; + _session->locations ()->find_all_between (_session->audible_sample (), + _session->audible_sample () + + 1, + locs, + Location::Flags (0)); + for (Locations::LocationList::iterator i = locs.begin (); + i != locs.end (); + ++i) { + if ((*i)->is_mark ()) { + _session->locations ()->remove (*i); + removed = true; + } + } + + // store undo + if (removed) { + _session->begin_reversible_command (_ ("remove marker")); + XMLNode& after = _session->locations ()->get_state (); + _session->add_command (new MementoCommand ( + *(_session->locations ()), &before, &after)); + _session->commit_reversible_command (); + } + } +} + +/* Locating */ + +void +SessionController::goto_zero () +{ + _session->request_locate (0); +} + +void +SessionController::goto_start (bool and_roll) +{ + _session->goto_start (and_roll); +} + +void +SessionController::goto_end () +{ + _session->goto_end (); +} + +struct SortLocationsByPosition { + bool operator() (Location* a, Location* b) + { + return a->start () < b->start (); + } +}; + +void +SessionController::goto_nth_marker (int n) +{ + if (!_session) { + return; + } + + const Locations::LocationList& l (_session->locations ()->list ()); + Locations::LocationList ordered; + ordered = l; + + SortLocationsByPosition cmp; + ordered.sort (cmp); + + for (Locations::LocationList::iterator i = ordered.begin (); + n >= 0 && i != ordered.end (); + ++i) { + if ((*i)->is_mark () && !(*i)->is_hidden () && + !(*i)->is_session_range ()) { + if (n == 0) { + _session->request_locate ((*i)->start ()); + break; + } + --n; + } + } +} + +void +SessionController::jump_by_seconds (double secs, LocateTransportDisposition ltd) +{ + samplepos_t current = _session->transport_sample (); + double s = (double)current / (double)_session->nominal_sample_rate (); + + s += secs; + if (s < 0) { + s = 0; + } + s = s * _session->nominal_sample_rate (); + + _session->request_locate (floor (s), ltd); +} + +void +SessionController::jump_by_bars (double bars, LocateTransportDisposition ltd) +{ + TempoMap& tmap (_session->tempo_map ()); + Timecode::BBT_Time bbt (tmap.bbt_at_sample (_session->transport_sample ())); + + bars += bbt.bars; + if (bars < 0) { + bars = 0; + } + + AnyTime any; + any.type = AnyTime::BBT; + any.bbt.bars = bars; + + _session->request_locate (_session->convert_to_samples (any), ltd); +} + +void +SessionController::jump_by_beats (double beats, LocateTransportDisposition ltd) +{ + TempoMap& tmap (_session->tempo_map ()); + double qn_goal = + tmap.quarter_note_at_sample (_session->transport_sample ()) + beats; + if (qn_goal < 0.0) { + qn_goal = 0.0; + } + _session->request_locate (tmap.sample_at_quarter_note (qn_goal), ltd); +} + +void +SessionController::locate (samplepos_t where, LocateTransportDisposition ltd) +{ + _session->request_locate (where, ltd); +} + +void +SessionController::locate (samplepos_t where, bool roll) +{ + _session->request_locate (where, roll ? MustRoll : RollIfAppropriate); +} + +void +SessionController::prev_marker () +{ + samplepos_t pos = + _session->locations ()->first_mark_before (_session->transport_sample ()); + + if (pos >= 0) { + _session->request_locate (pos); + } else { + _session->goto_start (); + } +} + +void +SessionController::next_marker () +{ + samplepos_t pos = + _session->locations ()->first_mark_after (_session->transport_sample ()); + + if (pos >= 0) { + _session->request_locate (pos); + } else { + _session->goto_end (); + } +} + +bool +SessionController::locating () const +{ + return _session->locate_pending (); +} + +bool +SessionController::locked () const +{ + return _session->transport_locked (); +} + +/* State */ + +void +SessionController::save_state () +{ + _session->save_state (""); +} + +/* Monitoring */ + +void +SessionController::toggle_click () +{ + bool state = !Config->get_clicking (); + Config->set_clicking (state); +} + +void +SessionController::midi_panic () +{ + _session->midi_panic (); +} + +void +SessionController::toggle_monitor_mute () +{ + if (_session->monitor_out ()) { + boost::shared_ptr mon = + _session->monitor_out ()->monitor_control (); + if (mon->cut_all ()) { + mon->set_cut_all (false); + } else { + mon->set_cut_all (true); + } + } +} + +void +SessionController::toggle_monitor_dim () +{ + if (_session->monitor_out ()) { + boost::shared_ptr mon = + _session->monitor_out ()->monitor_control (); + if (mon->dim_all ()) { + mon->set_dim_all (false); + } else { + mon->set_dim_all (true); + } + } +} + +void +SessionController::toggle_monitor_mono () +{ + if (_session->monitor_out ()) { + boost::shared_ptr mon = + _session->monitor_out ()->monitor_control (); + if (mon->mono ()) { + mon->set_mono (false); + } else { + mon->set_mono (true); + } + } +} + +void +SessionController::cancel_all_solo () +{ + if (_session) { + _session->cancel_all_solo (); + } +} + +/* Recording */ + +void +SessionController::toggle_punch_in () +{ + _session->config.set_punch_in (!_session->config.get_punch_in ()); +} + +void +SessionController::toggle_punch_out () +{ + _session->config.set_punch_out (!_session->config.get_punch_out ()); +} + +void +SessionController::set_record_enable (bool yn) +{ + if (yn) { + _session->maybe_enable_record (); + } else { + _session->disable_record (false, true); + } +} + +void +SessionController::rec_enable_toggle () +{ + switch (_session->record_status ()) { + case (RecordState)Disabled: + if (_session->ntracks () > 0) { + _session->maybe_enable_record (); + } + break; + case (RecordState)Recording: + case (RecordState)Enabled: + _session->disable_record (false, true); + } +} + +void +SessionController::toggle_all_rec_enables () +{ + if (_session->get_record_enabled ()) { + // _session->record_disenable_all (); + } else { + // _session->record_enable_all (); + } +} + +void +SessionController::all_tracks_rec_in () +{ + _session->set_all_tracks_record_enabled (true); +} + +void +SessionController::all_tracks_rec_out () +{ + _session->set_all_tracks_record_enabled (false); +} + +bool +SessionController::get_record_enabled () const +{ + return _session->get_record_enabled (); +} + +/* Time */ + +void +SessionController::timecode_time (samplepos_t where, Timecode::Time& timecode) +{ + _session->timecode_time (where, *((Timecode::Time*)&timecode)); +} diff --git a/libs/surfaces/control_protocol/wscript b/libs/surfaces/control_protocol/wscript index a16bedf949..90d787587f 100644 --- a/libs/surfaces/control_protocol/wscript +++ b/libs/surfaces/control_protocol/wscript @@ -10,6 +10,7 @@ controlcp_sources = [ 'basic_ui.cc', 'control_protocol.cc', 'midi_byte_array.cc', + 'session_controller.cc', ] def options(opt): diff --git a/libs/surfaces/faderport/faderport.cc b/libs/surfaces/faderport/faderport.cc index d4cfc1266d..8785ecfd1a 100644 --- a/libs/surfaces/faderport/faderport.cc +++ b/libs/surfaces/faderport/faderport.cc @@ -159,30 +159,30 @@ FaderPort::FaderPort (Session& s) get_button (FP_Touch).set_action (boost::bind (&FaderPort::off, this), false, LongPress); get_button (FP_Off).set_action (boost::bind (&FaderPort::off, this), true); - get_button (Play).set_action (boost::bind (&BasicUI::transport_play, this, true), true); - get_button (RecEnable).set_action (boost::bind (&BasicUI::rec_enable_toggle, this), true); + get_button (Play).set_action (boost::bind (&SessionController::transport_play, _controller, true), true); + get_button (RecEnable).set_action (boost::bind (&SessionController::rec_enable_toggle, _controller), true); /* Stop is a modifier, so we have to use its own button state to get the default action (since StopDown will be set when looking for the action to invoke. */ - get_button (Stop).set_action (boost::bind (&BasicUI::transport_stop, this), true, StopDown); - get_button (Ffwd).set_action (boost::bind (&BasicUI::ffwd, this), true); + get_button (Stop).set_action (boost::bind (&SessionController::transport_stop, _controller), true, StopDown); + get_button (Ffwd).set_action (boost::bind (&SessionController::ffwd, _controller), true); /* See comments about Stop above .. */ - get_button (Rewind).set_action (boost::bind (&BasicUI::rewind, this), true, RewindDown); - get_button (Rewind).set_action (boost::bind (&BasicUI::goto_zero, this), true, ButtonState (RewindDown|StopDown)); - get_button (Rewind).set_action (boost::bind (&BasicUI::goto_start, this, false), true, ButtonState (RewindDown|ShiftDown)); + get_button (Rewind).set_action (boost::bind (&SessionController::rewind, _controller), true, RewindDown); + get_button (Rewind).set_action (boost::bind (&SessionController::goto_zero, _controller), true, ButtonState (RewindDown|StopDown)); + get_button (Rewind).set_action (boost::bind (&SessionController::goto_start, _controller, false), true, ButtonState (RewindDown|ShiftDown)); - get_button (Ffwd).set_action (boost::bind (&BasicUI::ffwd, this), true); - get_button (Ffwd).set_action (boost::bind (&BasicUI::goto_end, this), true, ShiftDown); + get_button (Ffwd).set_action (boost::bind (&SessionController::ffwd, _controller), true); + get_button (Ffwd).set_action (boost::bind (&SessionController::goto_end, _controller), true, ShiftDown); get_button (Punch).set_action (boost::bind (&FaderPort::punch, this), true); - get_button (Loop).set_action (boost::bind (&BasicUI::loop_toggle, this), true); - get_button (Loop).set_action (boost::bind (&BasicUI::add_marker, this, string()), true, ShiftDown); + get_button (Loop).set_action (boost::bind (&SessionController::loop_toggle, _controller), true); + get_button (Loop).set_action (boost::bind (&SessionController::add_marker, _controller, string()), true, ShiftDown); - get_button (Punch).set_action (boost::bind (&BasicUI::prev_marker, this), true, ShiftDown); - get_button (User).set_action (boost::bind (&BasicUI::next_marker, this), true, ShiftDown); + get_button (Punch).set_action (boost::bind (&SessionController::prev_marker, _controller), true, ShiftDown); + get_button (User).set_action (boost::bind (&SessionController::next_marker, _controller), true, ShiftDown); get_button (Mute).set_action (boost::bind (&FaderPort::mute, this), true); get_button (Solo).set_action (boost::bind (&FaderPort::solo, this), true); @@ -686,7 +686,7 @@ FaderPort::map_transport_state () { get_button (Loop).set_led_state (_output_port, _session->get_play_loop()); - float ts = get_transport_speed(); + float ts = _controller.get_transport_speed(); if (ts == 0) { stop_blinking (Play); diff --git a/libs/surfaces/faderport8/actions.cc b/libs/surfaces/faderport8/actions.cc index 02a11f1579..e7d64214d1 100644 --- a/libs/surfaces/faderport8/actions.cc +++ b/libs/surfaces/faderport8/actions.cc @@ -135,22 +135,22 @@ FaderPort8::setup_actions () void FaderPort8::button_play () { - if (transport_rolling ()) { - if (get_transport_speed() != 1.0) { + if (_controller.transport_rolling ()) { + if (_controller.get_transport_speed() != 1.0) { _session->request_roll (TRS_UI); } else { - transport_stop (); + _controller.transport_stop (); } } else { - transport_play (); + _controller.transport_play (); } } void FaderPort8::button_stop () { - if (transport_rolling ()) { - transport_stop (); + if (_controller.transport_rolling ()) { + _controller.transport_stop (); } else { AccessAction ("Transport", "GotoStart"); } @@ -159,13 +159,13 @@ FaderPort8::button_stop () void FaderPort8::button_record () { - set_record_enable (!get_record_enabled ()); + _controller.set_record_enable (!_controller.get_record_enabled ()); } void FaderPort8::button_loop () { - loop_toggle (); + _controller.loop_toggle (); } void @@ -313,7 +313,7 @@ FaderPort8::button_varispeed (bool ffw) return; } - BasicUI::button_varispeed (ffw); + _controller.button_varispeed (ffw); } #ifdef FP8_MUTESOLO_UNDO @@ -336,7 +336,7 @@ FaderPort8::button_solo_clear () _solo_state.push_back (boost::weak_ptr(sc)); } } - cancel_all_solo (); // AccessAction ("Main", "cancel-solo"); + _controller.cancel_all_solo (); // AccessAction ("Main", "cancel-solo"); } else { /* restore solo */ boost::shared_ptr cl (new ControlList); @@ -384,7 +384,7 @@ FaderPort8::button_mute_clear () void FaderPort8::button_arm_all () { - BasicUI::all_tracks_rec_in (); + _controller.all_tracks_rec_in (); } /* access generic action */ @@ -513,9 +513,9 @@ FaderPort8::button_prev_next (bool next) break; case NavMarker: if (next) { - next_marker (); + _controller.next_marker (); } else { - prev_marker (); + _controller.prev_marker (); } break; } @@ -576,7 +576,7 @@ FaderPort8::button_encoder () } _session->locations()->next_available_name (markername,"mark"); - add_marker (markername); + _controller.add_marker (markername); } break; } diff --git a/libs/surfaces/faderport8/callbacks.cc b/libs/surfaces/faderport8/callbacks.cc index b2339adceb..c49b230ad3 100644 --- a/libs/surfaces/faderport8/callbacks.cc +++ b/libs/surfaces/faderport8/callbacks.cc @@ -125,11 +125,11 @@ FaderPort8::notify_parameter_changed (std::string param) void FaderPort8::notify_transport_state_changed () { - _ctrls.button (FP8Controls::BtnPlay).set_active (get_transport_speed()==1.0); - _ctrls.button (FP8Controls::BtnStop).set_active (get_transport_speed()==0.0); + _ctrls.button (FP8Controls::BtnPlay).set_active (_controller.get_transport_speed()==1.0); + _ctrls.button (FP8Controls::BtnStop).set_active (_controller.get_transport_speed()==0.0); /* set rewind/fastforward lights */ - const float ts = get_transport_speed(); + const float ts = _controller.get_transport_speed(); FP8ButtonInterface& b_rew = _ctrls.button (FP8Controls::BtnRewind); FP8ButtonInterface& b_ffw = _ctrls.button (FP8Controls::BtnFastForward); diff --git a/libs/surfaces/generic_midi/midifunction.cc b/libs/surfaces/generic_midi/midifunction.cc index 493f9c9ba7..6d0093622e 100644 --- a/libs/surfaces/generic_midi/midifunction.cc +++ b/libs/surfaces/generic_midi/midifunction.cc @@ -119,17 +119,17 @@ MIDIFunction::execute () break; case TransportStop: - _ui->transport_stop (); + _ui->controller().transport_stop (); DEBUG_TRACE (DEBUG::GenericMidi, "Function: transport_stop\n"); break; case TransportRoll: - _ui->transport_play (); + _ui->controller().transport_play (); DEBUG_TRACE (DEBUG::GenericMidi, "Function: transport_play\n"); break; case TransportStart: - _ui->goto_start (); + _ui->controller().goto_start (); DEBUG_TRACE (DEBUG::GenericMidi, "Function: goto_start\n"); break; @@ -139,27 +139,27 @@ MIDIFunction::execute () break; case TransportEnd: - _ui->goto_end (); + _ui->controller().goto_end (); DEBUG_TRACE (DEBUG::GenericMidi, "Function: goto_end\n"); break; case TransportLoopToggle: - _ui->loop_toggle (); + _ui->controller().loop_toggle (); DEBUG_TRACE (DEBUG::GenericMidi, "Function: loop_toggle\n"); break; case TransportRecordToggle: - _ui->rec_enable_toggle (); + _ui->controller().rec_enable_toggle (); DEBUG_TRACE (DEBUG::GenericMidi, "Function: toggle_record_enable\n"); break; case TransportRecordEnable: - _ui->set_record_enable (true); + _ui->controller().set_record_enable (true); DEBUG_TRACE (DEBUG::GenericMidi, "Function: set_record_enable = true\n"); break; case TransportRecordDisable: - _ui->set_record_enable (false); + _ui->controller().set_record_enable (false); DEBUG_TRACE (DEBUG::GenericMidi, "Function: set_record_enable = false\n"); break; @@ -168,7 +168,7 @@ MIDIFunction::execute () uint32_t rid; sscanf (_argument.c_str(), "%d", &rid); // XX fix me ... need to get stripable, not RID - //_ui->toggle_selection (rid, ARDOUR::PresentationInfo::Flag (ARDOUR::PresentationInfo::Route|ARDOUR::PresentationInfo::VCA)); + //_ui->controller().toggle_selection (rid, ARDOUR::PresentationInfo::Flag (ARDOUR::PresentationInfo::Route|ARDOUR::PresentationInfo::VCA)); DEBUG_TRACE (DEBUG::GenericMidi, string_compose ("Function: SetRouteSelection = %1\n", rid)); } break; diff --git a/libs/surfaces/launch_control_xl/controllers.cc b/libs/surfaces/launch_control_xl/controllers.cc index 7e595156e4..d689ead61a 100644 --- a/libs/surfaces/launch_control_xl/controllers.cc +++ b/libs/surfaces/launch_control_xl/controllers.cc @@ -1030,7 +1030,7 @@ LaunchControlXL::button_solo() void LaunchControlXL::button_solo_long_press() { - cancel_all_solo(); + _controller.cancel_all_solo(); } void diff --git a/libs/surfaces/mackie/jog_wheel.cc b/libs/surfaces/mackie/jog_wheel.cc index 0614c64888..93bb5c2e1e 100644 --- a/libs/surfaces/mackie/jog_wheel.cc +++ b/libs/surfaces/mackie/jog_wheel.cc @@ -73,9 +73,9 @@ void JogWheel::jog_event (float delta) break; default: if (delta > 0) { - _mcp.button_varispeed (true); + _mcp.controller ().button_varispeed (true); } else if (delta < 0) { - _mcp.button_varispeed (false); + _mcp.controller ().button_varispeed (false); } break; } diff --git a/libs/surfaces/mackie/mcp_buttons.cc b/libs/surfaces/mackie/mcp_buttons.cc index b9956fe9e5..5f15f2aeaf 100644 --- a/libs/surfaces/mackie/mcp_buttons.cc +++ b/libs/surfaces/mackie/mcp_buttons.cc @@ -370,7 +370,7 @@ LedState MackieControlProtocol::undo_press (Button&) { if (main_modifier_state() == MODIFIER_SHIFT) { - redo(); + redo (); } else { undo (); } @@ -387,7 +387,7 @@ LedState MackieControlProtocol::drop_press (Button &) { if (main_modifier_state() == MODIFIER_SHIFT) { - toggle_punch_in(); + _controller.toggle_punch_in(); return none; } else { access_action ("Common/start-range-from-playhead"); @@ -407,7 +407,7 @@ MackieControlProtocol::save_press (Button &) if (main_modifier_state() == MODIFIER_SHIFT) { quick_snapshot_switch(); } else { - save_state (); + _controller.save_state (); } return none; @@ -490,7 +490,7 @@ MackieControlProtocol::marker_release (Button &) } _session->locations()->next_available_name (markername,"mark"); - add_marker (markername); + _controller.add_marker (markername); return off; } @@ -502,7 +502,7 @@ MackieControlProtocol::marker_release (Button &) LedState MackieControlProtocol::stop_press (Button &) { - transport_stop (); + _controller.transport_stop (); if (main_modifier_state() == MODIFIER_SHIFT) { _session->midi_panic(); @@ -524,7 +524,7 @@ MackieControlProtocol::play_press (Button &) again, jump back to where we started last time */ - transport_play (get_transport_speed() == 1.0); + _controller.transport_play (_controller.get_transport_speed() == 1.0); return none; } @@ -537,7 +537,7 @@ MackieControlProtocol::play_release (Button &) LedState MackieControlProtocol::record_press (Button &) { - rec_enable_toggle (); + _controller.rec_enable_toggle (); return none; } @@ -551,13 +551,13 @@ LedState MackieControlProtocol::rewind_press (Button &) { if (modifier_state() & MODIFIER_MARKER) { - prev_marker (); + _controller.prev_marker (); } else if (modifier_state() & MODIFIER_NUDGE) { access_action ("Common/nudge-playhead-backward"); } else if (main_modifier_state() & MODIFIER_SHIFT) { - goto_start (); + _controller.goto_start (); } else { - rewind (); + _controller.rewind (); } return none; } @@ -572,13 +572,13 @@ LedState MackieControlProtocol::ffwd_press (Button &) { if (modifier_state() & MODIFIER_MARKER) { - next_marker (); + _controller.next_marker (); } else if (modifier_state() & MODIFIER_NUDGE) { access_action ("Common/nudge-playhead-forward"); } else if (main_modifier_state() & MODIFIER_SHIFT) { - goto_end(); + _controller.goto_end(); } else { - ffwd (); + _controller.ffwd (); } return none; } @@ -597,7 +597,7 @@ MackieControlProtocol::loop_press (Button &) return off; } else { bool was_on = _session->get_play_loop(); - loop_toggle (); + _controller.loop_toggle (); return was_on ? off : on; } } @@ -837,7 +837,7 @@ MackieControlProtocol::cancel_release (Button &) LedState MackieControlProtocol::user_a_press (Button &) { - transport_play (get_transport_speed() == 1.0); + _controller.transport_play (_controller.get_transport_speed() == 1.0); return off; } LedState @@ -848,7 +848,7 @@ MackieControlProtocol::user_a_release (Button &) LedState MackieControlProtocol::user_b_press (Button &) { - transport_stop(); + _controller.transport_stop(); return off; } LedState @@ -920,7 +920,7 @@ MackieControlProtocol::clearsolo_press (Mackie::Button&) return none; } - cancel_all_solo (); + _controller.cancel_all_solo (); return none; } @@ -1109,7 +1109,7 @@ Mackie::LedState MackieControlProtocol::replace_press (Mackie::Button&) { if (main_modifier_state() == MODIFIER_SHIFT) { - toggle_punch_out(); + _controller.toggle_punch_out(); return none; } else { access_action ("Common/finish-range-from-playhead"); diff --git a/libs/surfaces/mackie/strip.cc b/libs/surfaces/mackie/strip.cc index 6f71ea3338..ac93052250 100644 --- a/libs/surfaces/mackie/strip.cc +++ b/libs/surfaces/mackie/strip.cc @@ -1231,7 +1231,7 @@ Strip::notify_metering_state_changed() return; } - bool transport_is_rolling = (_surface->mcp().get_transport_speed () != 0.0f); + bool transport_is_rolling = (_surface->mcp().controller().get_transport_speed () != 0.0f); bool metering_active = _surface->mcp().metering_active (); if ((_transport_is_rolling == transport_is_rolling) && (_metering_active == metering_active)) { diff --git a/libs/surfaces/maschine2/callbacks.cc b/libs/surfaces/maschine2/callbacks.cc index ede1a39db4..ccce06b9c7 100644 --- a/libs/surfaces/maschine2/callbacks.cc +++ b/libs/surfaces/maschine2/callbacks.cc @@ -127,7 +127,7 @@ Maschine2::notify_record_state_changed () void Maschine2::notify_transport_state_changed () { - if (transport_rolling ()) { + if (_controller.transport_rolling ()) { _ctrl->button (M2Contols::Play)->set_color (COLOR_WHITE); } else { _ctrl->button (M2Contols::Play)->set_color (0); @@ -198,23 +198,23 @@ Maschine2::notify_history_changed () void Maschine2::button_play () { - if (transport_rolling ()) { - transport_stop (); + if (_controller.transport_rolling ()) { + _controller.transport_stop (); } else { - transport_play (); + _controller.transport_play (); } } void Maschine2::button_record () { - set_record_enable (!get_record_enabled ()); + _controller.set_record_enable (!_controller.get_record_enabled ()); } void Maschine2::button_loop () { - loop_toggle (); + _controller.loop_toggle (); } void @@ -226,7 +226,7 @@ Maschine2::button_metronom () void Maschine2::button_rewind () { - goto_start (transport_rolling ()); + _controller.goto_start (_controller.transport_rolling ()); } void diff --git a/libs/surfaces/osc/osc.cc b/libs/surfaces/osc/osc.cc index 1d67e8e60c..cd2e684c04 100644 --- a/libs/surfaces/osc/osc.cc +++ b/libs/surfaces/osc/osc.cc @@ -1279,7 +1279,7 @@ OSC::osc_toggle_roll (bool ret2strt) return 0; } - bool rolling = transport_rolling(); + bool rolling = _controller.transport_rolling(); if (rolling) { _session->request_stop (ret2strt, true); @@ -2915,7 +2915,7 @@ void OSC::transport_speed (lo_message msg) { check_surface (msg); - double ts = get_transport_speed(); + double ts = _controller.get_transport_speed(); lo_message reply = lo_message_new (); lo_message_add_double (reply, ts); @@ -2994,7 +2994,7 @@ OSC::jog (float delta, lo_message msg) { case 0: if (delta) { - jump_by_seconds (delta / 5); + _controller.jump_by_seconds (delta / 5); } break; case 1: @@ -3009,17 +3009,17 @@ OSC::jog (float delta, lo_message msg) break; case 3: if (delta) { - double speed = get_transport_speed (); - set_transport_speed (speed + (delta / 8.1)); + double speed = _controller.get_transport_speed (); + _controller.set_transport_speed (speed + (delta / 8.1)); } else { - set_transport_speed (0); + _controller.set_transport_speed (0); } break; case 4: if (delta > 0) { - next_marker (); + _controller.next_marker (); } else if (delta < 0) { - prev_marker (); + _controller.prev_marker (); } break; case 5: @@ -3055,8 +3055,8 @@ int OSC::jog_mode (float mode, lo_message msg) { OSCSurface *s = get_surface(get_address (msg)); - if (get_transport_speed () != 1.0) { - set_transport_speed (0); + if (_controller.get_transport_speed () != 1.0) { + _controller.set_transport_speed (0); } s->jogmode = (uint32_t) mode; s->global_obs->jog_mode (mode); diff --git a/libs/surfaces/osc/osc.h b/libs/surfaces/osc/osc.h index cd79b42719..486ac593d5 100644 --- a/libs/surfaces/osc/osc.h +++ b/libs/surfaces/osc/osc.h @@ -344,7 +344,7 @@ class OSC : public ARDOUR::ControlProtocol, public AbstractUI void record_enabled (lo_message msg); void add_marker_name(const std::string &markername) { - add_marker(markername); + _controller.add_marker(markername); } // cue @@ -416,38 +416,50 @@ class OSC : public ARDOUR::ControlProtocol, public AbstractUI return 0; \ } - PATH_CALLBACK(add_marker); - PATH_CALLBACK(loop_toggle); - PATH_CALLBACK(goto_start); - PATH_CALLBACK(goto_end); - PATH_CALLBACK(rewind); - PATH_CALLBACK(ffwd); - PATH_CALLBACK(transport_stop); - PATH_CALLBACK(transport_play); - PATH_CALLBACK(save_state); - PATH_CALLBACK(prev_marker); - PATH_CALLBACK(next_marker); +#define PATH_CONTROLLER_CALLBACK(name) \ + static int _ ## name (const char *path, const char *types, lo_arg **argv, int argc, lo_message msg, void *user_data) { \ + return static_cast(user_data)->cb_ ## name (path, types, argv, argc, msg); \ + } \ + int cb_ ## name (const char *path, const char *types, lo_arg ** argv, int argc, lo_message msg) { \ + OSC_DEBUG; \ + check_surface (msg); \ + if (argc > 0 && !strcmp (types, "f") && argv[0]->f != 1.0) { return 0; } \ + _controller.name (); \ + return 0; \ + } + + PATH_CONTROLLER_CALLBACK(add_marker); + PATH_CONTROLLER_CALLBACK(loop_toggle); + PATH_CONTROLLER_CALLBACK(goto_start); + PATH_CONTROLLER_CALLBACK(goto_end); + PATH_CONTROLLER_CALLBACK(rewind); + PATH_CONTROLLER_CALLBACK(ffwd); + PATH_CONTROLLER_CALLBACK(transport_stop); + PATH_CONTROLLER_CALLBACK(transport_play); + PATH_CONTROLLER_CALLBACK(save_state); + PATH_CONTROLLER_CALLBACK(prev_marker); + PATH_CONTROLLER_CALLBACK(next_marker); PATH_CALLBACK(undo); PATH_CALLBACK(redo); - PATH_CALLBACK(toggle_punch_in); - PATH_CALLBACK(toggle_punch_out); - PATH_CALLBACK(rec_enable_toggle); - PATH_CALLBACK(toggle_all_rec_enables); - PATH_CALLBACK(all_tracks_rec_in); - PATH_CALLBACK(all_tracks_rec_out); + PATH_CONTROLLER_CALLBACK(toggle_punch_in); + PATH_CONTROLLER_CALLBACK(toggle_punch_out); + PATH_CONTROLLER_CALLBACK(rec_enable_toggle); + PATH_CONTROLLER_CALLBACK(toggle_all_rec_enables); + PATH_CONTROLLER_CALLBACK(all_tracks_rec_in); + PATH_CONTROLLER_CALLBACK(all_tracks_rec_out); PATH_CALLBACK(cancel_all_solos); - PATH_CALLBACK(remove_marker_at_playhead); + PATH_CONTROLLER_CALLBACK(remove_marker_at_playhead); PATH_CALLBACK(mark_in); PATH_CALLBACK(mark_out); - PATH_CALLBACK(toggle_click); - PATH_CALLBACK(midi_panic); - PATH_CALLBACK(stop_forget); + PATH_CONTROLLER_CALLBACK(toggle_click); + PATH_CONTROLLER_CALLBACK(midi_panic); + PATH_CONTROLLER_CALLBACK(stop_forget); PATH_CALLBACK(set_punch_range); PATH_CALLBACK(set_loop_range); PATH_CALLBACK(set_session_range); - PATH_CALLBACK(toggle_monitor_mute); - PATH_CALLBACK(toggle_monitor_dim); - PATH_CALLBACK(toggle_monitor_mono); + PATH_CONTROLLER_CALLBACK(toggle_monitor_mute); + PATH_CONTROLLER_CALLBACK(toggle_monitor_dim); + PATH_CONTROLLER_CALLBACK(toggle_monitor_mono); PATH_CALLBACK(quick_snapshot_stay); PATH_CALLBACK(quick_snapshot_switch); PATH_CALLBACK(fit_1_track); @@ -484,12 +496,25 @@ class OSC : public ARDOUR::ControlProtocol, public AbstractUI return 0; \ } - PATH_CALLBACK1(set_transport_speed,f,); +#define PATH_CONTROLLER_CALLBACK1(name,type,optional) \ + static int _ ## name (const char *path, const char *types, lo_arg **argv, int argc, lo_message msg, void *user_data) { \ + return static_cast(user_data)->cb_ ## name (path, types, argv, argc, msg); \ + } \ + int cb_ ## name (const char *path, const char *types, lo_arg **argv, int argc, lo_message msg) { \ + OSC_DEBUG; \ + check_surface (msg); \ + if (argc > 0) { \ + _controller.name (optional argv[0]->type); \ + } \ + return 0; \ + } + + PATH_CONTROLLER_CALLBACK1(set_transport_speed,f,); PATH_CALLBACK1(add_marker_name,s,&); PATH_CALLBACK1(access_action,s,&); - PATH_CALLBACK1(jump_by_bars,f,); - PATH_CALLBACK1(jump_by_seconds,f,); + PATH_CONTROLLER_CALLBACK1(jump_by_bars,f,); + PATH_CONTROLLER_CALLBACK1(jump_by_seconds,f,); PATH_CALLBACK1(click_level,f,); #define PATH_CALLBACK1_MSG(name,arg1type) \ @@ -559,6 +584,19 @@ class OSC : public ARDOUR::ControlProtocol, public AbstractUI return 0; \ } +#define PATH_CONTROLLER_CALLBACK2(name,arg1type,arg2type) \ + static int _ ## name (const char *path, const char *types, lo_arg **argv, int argc, lo_message msg, void *user_data) { \ + return static_cast(user_data)->cb_ ## name (path, types, argv, argc, msg); \ + } \ + int cb_ ## name (const char *path, const char *types, lo_arg **argv, int argc, lo_message msg) { \ + OSC_DEBUG; \ + check_surface (msg); \ + if (argc > 1) { \ + _controller.name (argv[0]->arg1type, argv[1]->arg2type); \ + } \ + return 0; \ + } + #define PATH_CALLBACK2_MSG(name,arg1type,arg2type) \ static int _ ## name (const char *path, const char *types, lo_arg **argv, int argc, lo_message msg, void *user_data) { \ return static_cast(user_data)->cb_ ## name (path, types, argv, argc, msg); \ @@ -615,8 +653,8 @@ class OSC : public ARDOUR::ControlProtocol, public AbstractUI PATH_CALLBACK2_MSG(sel_eq_q,i,f); PATH_CALLBACK2_MSG(sel_eq_shape,i,f); - PATH_CALLBACK2(locate,i,i); - PATH_CALLBACK2(loop_location,i,i); + PATH_CONTROLLER_CALLBACK2(locate,i,i); + PATH_CONTROLLER_CALLBACK2(loop_location,i,i); PATH_CALLBACK3(route_set_send_gain_dB,i,i,f); PATH_CALLBACK3(route_set_send_fader,i,i,f); PATH_CALLBACK3(route_set_send_enable,i,i,f); diff --git a/libs/surfaces/push2/buttons.cc b/libs/surfaces/push2/buttons.cc index 5e506cf83c..e35d09a09f 100644 --- a/libs/surfaces/push2/buttons.cc +++ b/libs/surfaces/push2/buttons.cc @@ -360,7 +360,7 @@ Push2::button_play () } if (_modifier_state & ModShift) { - goto_start (_session->transport_rolling()); + _controller.goto_start (_session->transport_rolling()); return; } @@ -376,16 +376,16 @@ Push2::button_play () } if (_session->transport_rolling ()) { - transport_stop (); + _controller.transport_stop (); } else { - transport_play (); + _controller.transport_play (); } } void Push2::button_recenable () { - rec_enable_toggle (); + _controller.rec_enable_toggle (); } void @@ -427,19 +427,19 @@ Push2::button_left () void Push2::button_repeat () { - loop_toggle (); + _controller.loop_toggle (); } void Push2::button_metronome () { - toggle_click (); + _controller.toggle_click (); } void Push2::button_solo_long_press () { - cancel_all_solo (); + _controller.cancel_all_solo (); } void @@ -527,56 +527,56 @@ void Push2::button_fwd32t () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (0+n); + _controller.goto_nth_marker (0+n); } void Push2::button_fwd32 () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (1+n); + _controller.goto_nth_marker (1+n); } void Push2::button_fwd16t () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (2+n); + _controller.goto_nth_marker (2+n); } void Push2::button_fwd16 () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (3+n); + _controller.goto_nth_marker (3+n); } void Push2::button_fwd8t () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (4+n); + _controller.goto_nth_marker (4+n); } void Push2::button_fwd8 () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (5+n); + _controller.goto_nth_marker (5+n); } void Push2::button_fwd4t () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (6+n); + _controller.goto_nth_marker (6+n); } void Push2::button_fwd4 () { const int n = (_modifier_state & ModShift) ? 8 : 0; - goto_nth_marker (7+n); + _controller.goto_nth_marker (7+n); } void diff --git a/libs/surfaces/push2/push2.cc b/libs/surfaces/push2/push2.cc index e8b536fab5..097f72a09a 100644 --- a/libs/surfaces/push2/push2.cc +++ b/libs/surfaces/push2/push2.cc @@ -764,7 +764,7 @@ Push2::handle_midi_note_on_message (MIDI::Parser& parser, MIDI::EventTwoBytes* e /* touch strip */ case 12: if (ev->velocity < 64) { - transport_stop (); + _controller.transport_stop (); } break; } diff --git a/libs/surfaces/us2400/mcp_buttons.cc b/libs/surfaces/us2400/mcp_buttons.cc index 314ef4e69b..7f5acb1503 100644 --- a/libs/surfaces/us2400/mcp_buttons.cc +++ b/libs/surfaces/us2400/mcp_buttons.cc @@ -380,7 +380,7 @@ US2400Protocol::save_press (Button &) if (main_modifier_state() == MODIFIER_SHIFT) { quick_snapshot_switch(); } else { - save_state (); + _controller.save_state (); } return none; @@ -463,7 +463,7 @@ US2400Protocol::marker_release (Button &) } _session->locations()->next_available_name (markername,"mark"); - add_marker (markername); + _controller.add_marker (markername); return off; } @@ -475,7 +475,7 @@ US2400Protocol::marker_release (Button &) LedState US2400Protocol::stop_press (Button &) { - transport_stop (); + _controller.transport_stop (); if (main_modifier_state() == MODIFIER_SHIFT) { _session->midi_panic(); @@ -497,7 +497,7 @@ US2400Protocol::play_press (Button &) again, jump back to where we started last time */ - transport_play (get_transport_speed() == 1.0); + _controller.transport_play (_controller.get_transport_speed() == 1.0); return none; } @@ -510,7 +510,7 @@ US2400Protocol::play_release (Button &) LedState US2400Protocol::record_press (Button &) { - rec_enable_toggle (); + _controller.rec_enable_toggle (); return none; } @@ -524,13 +524,13 @@ LedState US2400Protocol::rewind_press (Button &) { if (modifier_state() & MODIFIER_MARKER) { - prev_marker (); + _controller.prev_marker (); } else if ( (_modifier_state & MODIFIER_DROP) == MODIFIER_DROP) { access_action ("Common/start-range-from-playhead"); } else if (main_modifier_state() & MODIFIER_SHIFT) { - goto_start (); + _controller.goto_start (); } else { - rewind (); + _controller.rewind (); } return none; } @@ -545,13 +545,13 @@ LedState US2400Protocol::ffwd_press (Button &) { if (modifier_state() & MODIFIER_MARKER) { - next_marker (); + _controller.next_marker (); } else if ( (_modifier_state & MODIFIER_DROP) == MODIFIER_DROP) { access_action ("Common/finish-range-from-playhead"); } else if (main_modifier_state() & MODIFIER_SHIFT) { - goto_end(); + _controller.goto_end(); } else { - ffwd (); + _controller.ffwd (); } return none; } @@ -570,7 +570,7 @@ US2400Protocol::loop_press (Button &) return off; } else { bool was_on = _session->get_play_loop(); - loop_toggle (); + _controller.loop_toggle (); return was_on ? off : on; } } @@ -821,7 +821,7 @@ US2400Protocol::cancel_release (Button &) LedState US2400Protocol::user_a_press (Button &) { - transport_play (get_transport_speed() == 1.0); + _controller.transport_play (_controller.get_transport_speed() == 1.0); return off; } LedState @@ -832,7 +832,7 @@ US2400Protocol::user_a_release (Button &) LedState US2400Protocol::user_b_press (Button &) { - transport_stop(); + _controller.transport_stop(); return off; } LedState @@ -897,7 +897,7 @@ US2400Protocol::clearsolo_press (US2400::Button&) { // clears all solos and listens (pfl/afl) if (main_modifier_state() & MODIFIER_OPTION) { - cancel_all_solo (); + _controller.cancel_all_solo (); } return none; @@ -1082,7 +1082,7 @@ US2400::LedState US2400Protocol::replace_press (US2400::Button&) { if (main_modifier_state() == MODIFIER_SHIFT) { - toggle_punch_out(); + _controller.toggle_punch_out(); return none; } else { access_action ("Common/finish-range-from-playhead"); diff --git a/libs/surfaces/us2400/strip.cc b/libs/surfaces/us2400/strip.cc index 89925a2222..812f46c506 100644 --- a/libs/surfaces/us2400/strip.cc +++ b/libs/surfaces/us2400/strip.cc @@ -993,7 +993,7 @@ Strip::notify_metering_state_changed() return; } - bool transport_is_rolling = (_surface->mcp().get_transport_speed () != 0.0f); + bool transport_is_rolling = (_surface->mcp().controller ().get_transport_speed () != 0.0f); bool metering_active = _surface->mcp().metering_active (); if ((_transport_is_rolling == transport_is_rolling) && (_metering_active == metering_active)) { diff --git a/libs/surfaces/websockets/transport.cc b/libs/surfaces/websockets/transport.cc index a32188da1d..3e7328f47b 100644 --- a/libs/surfaces/websockets/transport.cc +++ b/libs/surfaces/websockets/transport.cc @@ -50,7 +50,7 @@ ArdourTransport::time () const bool ArdourTransport::roll () const { - return basic_ui ().transport_rolling (); + return basic_ui ().controller ().transport_rolling (); } void @@ -58,7 +58,7 @@ ArdourTransport::set_roll (bool value) { if ((value && !roll ()) || (!value && roll ())) { // this call is equivalent to hitting the spacebar - basic_ui ().toggle_roll (false); + basic_ui ().controller ().toggle_roll (false); } } @@ -72,6 +72,6 @@ void ArdourTransport::set_record (bool value) { if ((value && !record ()) || (!value && record ())) { - basic_ui ().rec_enable_toggle (); + basic_ui ().controller ().rec_enable_toggle (); } } diff --git a/libs/surfaces/wiimote/wiimote.cc b/libs/surfaces/wiimote/wiimote.cc index 12a636f882..9d38529de5 100644 --- a/libs/surfaces/wiimote/wiimote.cc +++ b/libs/surfaces/wiimote/wiimote.cc @@ -299,7 +299,7 @@ WiimoteControlProtocol::update_led_state () } // enable LED1 if Ardour is playing - if (transport_rolling ()) { + if (_controller.transport_rolling ()) { DEBUG_TRACE (DEBUG::WiimoteControl, "WiimoteControlProtocol::update_led_state playing, activate LED1\n"); state |= CWIID_LED1_ON; } @@ -365,12 +365,12 @@ WiimoteControlProtocol::wiimote_callback (int mesg_count, union cwiid_mesg mesg[ // B + up = move playhead to next marker if (b & CWIID_BTN_UP) { - next_marker (); + _controller.next_marker (); } // B + down = move playhead to prev marker if (b & CWIID_BTN_DOWN) { - prev_marker (); + _controller.prev_marker (); } // B + Home = add marker at playhead @@ -400,7 +400,7 @@ WiimoteControlProtocol::wiimote_callback (int mesg_count, union cwiid_mesg mesg[ // 2 = enable recording in general if (b & CWIID_BTN_2) { - rec_enable_toggle (); + _controller.rec_enable_toggle (); } // left = move playhead back a bit