X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;ds=sidebyside;f=libs%2Fsurfaces%2Ffaderport8%2Ffaderport8.cc;h=5e5cf498f739ed0d2b0037f1f3a9157231d9e38e;hb=7b1a875f9c736b419285318147b3dc6b9c0a0e00;hp=0ffa70a0aa7cb180ce91ff31d7aebe7e8e880c7a;hpb=d5d297c4071240d8a462fa22d53dba03cbdc211d;p=ardour.git diff --git a/libs/surfaces/faderport8/faderport8.cc b/libs/surfaces/faderport8/faderport8.cc index 0ffa70a0aa..5e5cf498f7 100644 --- a/libs/surfaces/faderport8/faderport8.cc +++ b/libs/surfaces/faderport8/faderport8.cc @@ -1,20 +1,21 @@ /* - * Copyright (C) 2017 Robin Gareus - * Copyright (C) 2015 Paul Davis + * Copyright (C) 2017-2018 Ben Loftis + * Copyright (C) 2017-2018 Robin Gareus + * Copyright (C) 2017 Paul Davis * - * 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 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. + * 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 @@ -37,6 +38,7 @@ #include "ardour/debug.h" #include "ardour/midi_track.h" #include "ardour/midiport_manager.h" +#include "ardour/panner_shell.h" #include "ardour/plugin.h" #include "ardour/plugin_insert.h" #include "ardour/processor.h" @@ -50,11 +52,11 @@ #include "faderport8.h" using namespace ARDOUR; -using namespace ArdourSurface; using namespace PBD; using namespace Glib; using namespace std; -using namespace ArdourSurface::FP8Types; +using namespace ArdourSurface::FP_NAMESPACE; +using namespace ArdourSurface::FP_NAMESPACE::FP8Types; #include "pbd/i18n.h" @@ -86,22 +88,29 @@ debug_2byte_msg (std::string const& msg, int b0, int b1) } FaderPort8::FaderPort8 (Session& s) +#ifdef FADERPORT16 + : ControlProtocol (s, _("PreSonus FaderPort16")) +#elif defined FADERPORT2 + : ControlProtocol (s, _("PreSonus FaderPort2")) +#else : ControlProtocol (s, _("PreSonus FaderPort8")) +#endif , AbstractUI (name()) , _connection_state (ConnectionState (0)) , _device_active (false) , _ctrls (*this) - , _channel_off (0) , _plugin_off (0) , _parameter_off (0) , _show_presets (false) , _showing_well_known (0) + , _timer_divider (0) , _blink_onoff (false) , _shift_lock (false) , _shift_pressed (0) , gui (0) , _link_enabled (false) , _link_locked (false) + , _chan_locked (false) , _clock_mode (1) , _scribble_mode (2) , _two_line_text (false) @@ -110,8 +119,16 @@ FaderPort8::FaderPort8 (Session& s) boost::shared_ptr inp; boost::shared_ptr outp; +#ifdef FADERPORT16 + inp = AudioEngine::instance()->register_input_port (DataType::MIDI, "FaderPort16 Recv", true); + outp = AudioEngine::instance()->register_output_port (DataType::MIDI, "FaderPort16 Send", true); +#elif defined FADERPORT2 + inp = AudioEngine::instance()->register_input_port (DataType::MIDI, "FaderPort2 Recv", true); + outp = AudioEngine::instance()->register_output_port (DataType::MIDI, "FaderPort2 Send", true); +#else inp = AudioEngine::instance()->register_input_port (DataType::MIDI, "FaderPort8 Recv", true); outp = AudioEngine::instance()->register_output_port (DataType::MIDI, "FaderPort8 Send", true); +#endif _input_port = boost::dynamic_pointer_cast(inp); _output_port = boost::dynamic_pointer_cast(outp); @@ -119,8 +136,16 @@ FaderPort8::FaderPort8 (Session& s) throw failed_constructor(); } +#ifdef FADERPORT16 + _input_bundle.reset (new ARDOUR::Bundle (_("FaderPort16 (Receive)"), true)); + _output_bundle.reset (new ARDOUR::Bundle (_("FaderPort16 (Send)"), false)); +#elif defined FADERPORT2 + _input_bundle.reset (new ARDOUR::Bundle (_("FaderPort2 (Receive)"), true)); + _output_bundle.reset (new ARDOUR::Bundle (_("FaderPort2 (Send)"), false)); +#else _input_bundle.reset (new ARDOUR::Bundle (_("FaderPort8 (Receive)"), true)); - _output_bundle.reset (new ARDOUR::Bundle (_("FaderPort8 (Send) "), false)); + _output_bundle.reset (new ARDOUR::Bundle (_("FaderPort8 (Send)"), false)); +#endif _input_bundle->add_channel ( inp->name(), @@ -142,7 +167,7 @@ FaderPort8::FaderPort8 (Session& s) setup_actions (); _ctrls.FaderModeChanged.connect_same_thread (modechange_connections, boost::bind (&FaderPort8::notify_fader_mode_changed, this)); - _ctrls.MixModeChanged.connect_same_thread (modechange_connections, boost::bind (&FaderPort8::assign_strips, this, true)); + _ctrls.MixModeChanged.connect_same_thread (modechange_connections, boost::bind (&FaderPort8::assign_strips, this)); } FaderPort8::~FaderPort8 () @@ -156,6 +181,7 @@ FaderPort8::~FaderPort8 () if (_input_port) { DEBUG_TRACE (DEBUG::FaderPort8, string_compose ("unregistering input port %1\n", boost::shared_ptr(_input_port)->name())); + Glib::Threads::Mutex::Lock em (AudioEngine::instance()->process_lock()); AudioEngine::instance()->unregister_port (_input_port); _input_port.reset (); } @@ -165,6 +191,7 @@ FaderPort8::~FaderPort8 () if (_output_port) { _output_port->drain (10000, 250000); /* check every 10 msecs, wait up to 1/4 second for the port to drain */ DEBUG_TRACE (DEBUG::FaderPort8, string_compose ("unregistering output port %1\n", boost::shared_ptr(_output_port)->name())); + Glib::Threads::Mutex::Lock em (AudioEngine::instance()->process_lock()); AudioEngine::instance()->unregister_port (_output_port); _output_port.reset (); } @@ -204,25 +231,17 @@ FaderPort8::stop () DEBUG_TRACE (DEBUG::FaderPort8, "BaseUI::quit ()\n"); BaseUI::quit (); close (); // drop references, disconnect from session signals - return 0; } void FaderPort8::thread_init () { - struct sched_param rtparam; - pthread_set_name (event_loop_name().c_str()); PBD::notify_event_loops_about_thread_creation (pthread_self(), event_loop_name(), 2048); ARDOUR::SessionEvent::create_per_thread_pool (event_loop_name(), 128); - memset (&rtparam, 0, sizeof (rtparam)); - rtparam.sched_priority = 9; /* XXX should be relative to audio (JACK) thread */ - - if (pthread_setschedparam (pthread_self(), SCHED_FIFO, &rtparam) != 0) { - // do we care? not particularly. - } + set_thread_priority (); } bool @@ -237,7 +256,7 @@ FaderPort8::periodic () _timecode = Timecode::timecode_format_time(TC); char buf[16]; - Timecode::BBT_Time BBT = session->tempo_map ().bbt_at_frame (session->transport_frame ()); + Timecode::BBT_Time BBT = session->tempo_map ().bbt_at_sample (session->transport_sample ()); snprintf (buf, sizeof (buf), " %02" PRIu32 "|%02" PRIu32 "|%02" PRIu32 "|%02" PRIu32, BBT.bars % 100, BBT.beats %100, @@ -248,6 +267,14 @@ FaderPort8::periodic () _musical_time.clear (); } +#ifdef FADERPORT16 + /* every second, send "running" */ + if (++_timer_divider == 10) { + _timer_divider = 0; + tx_midi3 (0xa0, 0x00, 0x00); + } +#endif + /* update stripables */ Periodic (); return true; @@ -292,7 +319,7 @@ FaderPort8::close () DEBUG_TRACE (DEBUG::FaderPort8, "FaderPort8::close\n"); stop_midi_handling (); session_connections.drop_connections (); - automation_state_connections.drop_connections (); + route_state_connections.drop_connections (); assigned_stripable_connections.drop_connections (); _assigned_strips.clear (); drop_ctrl_connections (); @@ -324,10 +351,12 @@ FaderPort8::connected () // ideally check firmware version >= 1.01 (USB bcdDevice 0x0101) (vendor 0x194f prod 0x0202) // but we don't have a handle to the underlying USB device here. - _channel_off = _plugin_off = _parameter_off = 0; + memset (_channel_off, 0, sizeof (_channel_off)); + _plugin_off = _parameter_off = 0; _blink_onoff = false; _shift_lock = false; _shift_pressed = 0; + _timer_divider = 0; start_midi_handling (); _ctrls.initialize (); @@ -342,7 +371,7 @@ FaderPort8::connected () tx_midi3 (0x90, 0x46, 0x00); send_session_state (); - assign_strips (true); + assign_strips (); Glib::RefPtr blink_timer = Glib::TimeoutSource::create (200); @@ -360,7 +389,7 @@ FaderPort8::disconnected () { stop_midi_handling (); if (_device_active) { - for (uint8_t id = 0; id < 8; ++id) { + for (uint8_t id = 0; id < N_STRIPS; ++id) { _ctrls.strip(id).unset_controllables (); } _ctrls.all_lights_off (); @@ -485,7 +514,7 @@ FaderPort8::midi_input_handler (Glib::IOCondition ioc, boost::weak_ptr(port)->name())); #endif - framepos_t now = session->engine().sample_time(); + samplepos_t now = session->engine().sample_time(); port->parse (now); } @@ -559,13 +588,25 @@ void FaderPort8::controller_handler (MIDI::Parser &, MIDI::EventTwoBytes* tb) { debug_2byte_msg ("CC", tb->controller_number, tb->value); - // encoder - // val Bit 7 = direction, Bits 0-6 = number of steps + /* encoder + * val Bit 6 = direction, Bits 0-5 = number of steps + */ + static const uint8_t dir_mask = 0x40; + static const uint8_t step_mask = 0x3f; + if (tb->controller_number == 0x3c) { - encoder_navigate (tb->value & 0x40 ? true : false, tb->value & 0x3f); + encoder_navigate (tb->value & dir_mask ? true : false, tb->value & step_mask); } if (tb->controller_number == 0x10) { - encoder_parameter (tb->value & 0x40 ? true : false, tb->value & 0x3f); +#ifdef FADERPORT2 + if (_ctrls.nav_mode() == NavPan) { + encoder_parameter (tb->value & dir_mask ? true : false, tb->value & step_mask); + } else { + encoder_navigate (tb->value & dir_mask ? true : false, tb->value & step_mask); + } +#else + encoder_parameter (tb->value & dir_mask ? true : false, tb->value & step_mask); +#endif } } @@ -575,7 +616,12 @@ FaderPort8::note_on_handler (MIDI::Parser &, MIDI::EventTwoBytes* tb) debug_2byte_msg ("ON", tb->note_number, tb->velocity); /* fader touch */ - if (tb->note_number >= 0x68 && tb->note_number <= 0x6f) { +#ifdef FADERPORT16 + static const uint8_t touch_id_uppper = 0x77; +#else + static const uint8_t touch_id_uppper = 0x6f; +#endif + if (tb->note_number >= 0x68 && tb->note_number <= touch_id_uppper) { _ctrls.midi_touch (tb->note_number - 0x68, tb->velocity); return; } @@ -614,7 +660,12 @@ FaderPort8::note_off_handler (MIDI::Parser &, MIDI::EventTwoBytes* tb) { debug_2byte_msg ("OF", tb->note_number, tb->velocity); - if (tb->note_number >= 0x68 && tb->note_number <= 0x6f) { +#ifdef FADERPORT16 + static const uint8_t touch_id_uppper = 0x77; +#else + static const uint8_t touch_id_uppper = 0x6f; +#endif + if (tb->note_number >= 0x68 && tb->note_number <= touch_id_uppper) { // fader touch _ctrls.midi_touch (tb->note_number - 0x68, tb->velocity); return; @@ -707,8 +758,11 @@ FaderPort8::get_state () child->add_child_nocopy (boost::shared_ptr(_output_port)->get_state()); node.add_child_nocopy (*child); +#ifndef FADERPORT2 node.set_property (X_("clock-mode"), _clock_mode); node.set_property (X_("scribble-mode"), _scribble_mode); + node.set_property (X_("two-line-text"), _two_line_text); +#endif for (UserActionMap::const_iterator i = _user_action_map.begin (); i != _user_action_map.end (); ++i) { if (i->second.empty()) { @@ -762,6 +816,7 @@ FaderPort8::set_state (const XMLNode& node, int version) node.get_property (X_("clock-mode"), _clock_mode); node.get_property (X_("scribble-mode"), _scribble_mode); + node.get_property (X_("two-line-text"), _two_line_text); _user_action_map.clear (); // TODO: When re-loading state w/o surface re-init becomes possible, @@ -904,7 +959,7 @@ FaderPort8::filter_stripables (StripableList& strips) const break; default: assert (0); - // fall through + /* fallthrough */ case MixAll: allow_master = true; flt = &flt_all; @@ -939,12 +994,24 @@ FaderPort8::assign_stripables (bool select_only) set_periodic_display_mode (FP8Strip::Stripables); } +#ifdef FADERPORT2 + boost::shared_ptr s = first_selected_stripable(); + if (s) { + _ctrls.strip(0).set_stripable (s, _ctrls.fader_mode() == ModePan); + } else { + _ctrls.strip(0).unset_controllables ( FP8Strip::CTRL_ALL ); + } + return; +#endif + int n_strips = strips.size(); - _channel_off = std::min (_channel_off, n_strips - 8); - _channel_off = std::max (0, _channel_off); + int channel_off = get_channel_off (_ctrls.mix_mode ()); + channel_off = std::min (channel_off, n_strips - N_STRIPS); + channel_off = std::max (0, channel_off); + set_channel_off (_ctrls.mix_mode (), channel_off); uint8_t id = 0; - int skip = _channel_off; + int skip = channel_off; for (StripableList::const_iterator s = strips.begin(); s != strips.end(); ++s) { if (skip > 0) { --skip; @@ -960,10 +1027,17 @@ FaderPort8::assign_stripables (bool select_only) (*s)->presentation_info ().PropertyChanged.connect (assigned_stripable_connections, MISSING_INVALIDATOR, boost::bind (&FaderPort8::notify_stripable_property_changed, this, boost::weak_ptr (*s), _1), this); + if (boost::shared_ptr r = boost::dynamic_pointer_cast(*s)) { + if (r->panner_shell()) { + r->panner_shell()->Changed.connect (assigned_stripable_connections, MISSING_INVALIDATOR, + boost::bind (&FaderPort8::notify_stripable_property_changed, this, boost::weak_ptr (*s), PropertyChange()), this); + } + } + if (select_only) { /* used in send mode */ _ctrls.strip(id).set_text_line (3, (*s)->name (), true); - _ctrls.strip(id).select_button ().set_color ((*s)->presentation_info ().color()); + _ctrls.strip(id).set_select_button_color ((*s)->presentation_info ().color()); /* update selection lights */ _ctrls.strip(id).select_button ().set_active ((*s)->is_selected ()); _ctrls.strip(id).select_button ().set_blinking (*s == first_selected_stripable ()); @@ -974,11 +1048,11 @@ FaderPort8::assign_stripables (bool select_only) boost::function cb (boost::bind (&FaderPort8::select_strip, this, boost::weak_ptr (*s))); _ctrls.strip(id).set_select_cb (cb); - if (++id == 8) { + if (++id == N_STRIPS) { break; } } - for (; id < 8; ++id) { + for (; id < N_STRIPS; ++id) { _ctrls.strip(id).unset_controllables (select_only ? (FP8Strip::CTRL_SELECT | FP8Strip::CTRL_TEXT3) : FP8Strip::CTRL_ALL); _ctrls.strip(id).set_periodic_display_mode (FP8Strip::Stripables); } @@ -1108,7 +1182,7 @@ FaderPort8::assign_processor_ctrls () int n_parameters = std::max (toggle_params.size(), slider_params.size()); - _parameter_off = std::min (_parameter_off, n_parameters - 8); + _parameter_off = std::min (_parameter_off, n_parameters - N_STRIPS); _parameter_off = std::max (0, _parameter_off); uint8_t id = 0; @@ -1132,13 +1206,13 @@ FaderPort8::assign_processor_ctrls () _ctrls.strip(id).set_select_controllable (toggle_params[i]->ac); _ctrls.strip(id).set_text_line (3, toggle_params[i]->name, true); } - if (++id == 8) { + if (++id == N_STRIPS) { break; } } // clear remaining - for (; id < 8; ++id) { + for (; id < N_STRIPS; ++id) { _ctrls.strip(id).unset_controllables (); } } @@ -1158,7 +1232,7 @@ FaderPort8::assign_plugin_presets (boost::shared_ptr pi) int n_parameters = presets.size (); - _parameter_off = std::min (_parameter_off, n_parameters - 7); + _parameter_off = std::min (_parameter_off, n_parameters - (N_STRIPS - 1)); _parameter_off = std::max (0, _parameter_off); Plugin::PresetRecord active = plugin->last_preset (); @@ -1179,18 +1253,18 @@ FaderPort8::assign_plugin_presets (boost::shared_ptr pi) _ctrls.strip(id).set_text_line (0, label.substr (0, 9)); _ctrls.strip(id).set_text_line (1, label.length () > 9 ? label.substr (9) : ""); _ctrls.strip(id).set_text_line (3, "PRESET", true); - if (++id == 7) { + if (++id == (N_STRIPS - 1)) { break; } } // clear remaining - for (; id < 7; ++id) { + for (; id < (N_STRIPS - 1); ++id) { _ctrls.strip(id).unset_controllables (); } // pin clear-preset to the last slot - assert (id == 7); + assert (id == (N_STRIPS - 1)); _ctrls.strip(id).unset_controllables (FP8Strip::CTRL_ALL & ~FP8Strip::CTRL_TEXT0 & ~FP8Strip::CTRL_TEXT3 & ~FP8Strip::CTRL_SELECT); boost::function cb (boost::bind (&FaderPort8::select_plugin_preset, this, SIZE_MAX)); _ctrls.strip(id).set_select_cb (cb); @@ -1231,6 +1305,7 @@ FaderPort8::build_well_known_processor_ctrls (boost::shared_ptr s, bo } else { PUSH_BACK_NON_NULL ("Comp In", s->comp_enable_controllable ()); PUSH_BACK_NON_NULL ("Threshold", s->comp_threshold_controllable ()); + PUSH_BACK_NON_NULL ("Makeup", s->comp_makeup_controllable ()); PUSH_BACK_NON_NULL ("Speed", s->comp_speed_controllable ()); PUSH_BACK_NON_NULL ("Mode", s->comp_mode_controllable ()); } @@ -1394,12 +1469,14 @@ FaderPort8::spill_plugins () for (uint32_t i = 0; 0 != (proc = r->nth_plugin (i)); ++i) { if (!proc->display_to_user ()) { + continue; + } #ifdef MIXBUS - boost::shared_ptr pi = boost::dynamic_pointer_cast (proc); - if (pi->is_channelstrip ()) // don't skip MB PRE -#endif + /* don't show channelstrip plugins, use "well known" */ + if (boost::dynamic_pointer_cast (proc)->is_channelstrip ()) { continue; } +#endif int n_controls = 0; set p = proc->what_can_be_automated (); for (set::iterator j = p.begin(); j != p.end(); ++j) { @@ -1415,7 +1492,7 @@ FaderPort8::spill_plugins () } int n_plugins = procs.size(); - int spillwidth = 8; + int spillwidth = N_STRIPS; bool have_well_known_eq = false; bool have_well_known_comp = false; @@ -1473,7 +1550,7 @@ FaderPort8::spill_plugins () } if (have_well_known_comp) { - assert (id < 8); + assert (id < N_STRIPS); boost::function cb (boost::bind (&FaderPort8::select_plugin, this, -2)); _ctrls.strip(id).unset_controllables (FP8Strip::CTRL_ALL & ~FP8Strip::CTRL_TEXT & ~FP8Strip::CTRL_SELECT); _ctrls.strip(id).set_select_cb (cb); @@ -1487,7 +1564,7 @@ FaderPort8::spill_plugins () ++id; } if (have_well_known_eq) { - assert (id < 8); + assert (id < N_STRIPS); boost::function cb (boost::bind (&FaderPort8::select_plugin, this, -1)); _ctrls.strip(id).unset_controllables (FP8Strip::CTRL_ALL & ~FP8Strip::CTRL_TEXT & ~FP8Strip::CTRL_SELECT); _ctrls.strip(id).set_select_cb (cb); @@ -1500,7 +1577,7 @@ FaderPort8::spill_plugins () _ctrls.strip(id).set_text_line (3, ""); ++id; } - assert (id == 8); + assert (id == N_STRIPS); } /* **************************************************************************** @@ -1530,7 +1607,7 @@ FaderPort8::assign_sends () set_periodic_display_mode (FP8Strip::SendDisplay); - _plugin_off = std::min (_plugin_off, n_sends - 8); + _plugin_off = std::min (_plugin_off, n_sends - N_STRIPS); _plugin_off = std::max (0, _plugin_off); uint8_t id = 0; @@ -1550,16 +1627,16 @@ FaderPort8::assign_sends () _ctrls.strip(id).set_text_line (0, s->send_name (i)); _ctrls.strip(id).set_mute_controllable (s->send_enable_controllable (i)); - if (++id == 8) { + if (++id == N_STRIPS) { break; } } // clear remaining - for (; id < 8; ++id) { + for (; id < N_STRIPS; ++id) { _ctrls.strip(id).unset_controllables (FP8Strip::CTRL_ALL & ~FP8Strip::CTRL_TEXT3 & ~FP8Strip::CTRL_SELECT); } #ifdef MIXBUS // master-assign on last solo - _ctrls.strip(7).set_solo_controllable (s->master_send_enable_controllable ()); + _ctrls.strip(N_STRIPS - 1).set_solo_controllable (s->master_send_enable_controllable ()); #endif /* set select buttons */ assigned_stripable_connections.drop_connections (); @@ -1572,12 +1649,8 @@ FaderPort8::assign_sends () */ void -FaderPort8::assign_strips (bool reset_bank) +FaderPort8::assign_strips () { - if (reset_bank) { - _channel_off = 0; - } - assigned_stripable_connections.drop_connections (); _assigned_strips.clear (); @@ -1608,7 +1681,7 @@ FaderPort8::assign_strips (bool reset_bank) void FaderPort8::set_periodic_display_mode (FP8Strip::DisplayMode m) { - for (uint8_t id = 0; id < 8; ++id) { + for (uint8_t id = 0; id < N_STRIPS; ++id) { _ctrls.strip(id).set_periodic_display_mode (m); } } @@ -1639,6 +1712,18 @@ FaderPort8::select_strip (boost::weak_ptr ws) return; } #if 1 /* single exclusive selection by default, toggle via shift */ + +# if 1 /* selecting a selected strip -> move fader to unity */ + if (s == first_selected_stripable () && !shift_mod ()) { + if (_ctrls.fader_mode () == ModeTrack) { + boost::shared_ptr ac = s->gain_control (); + ac->start_touch (ac->session().transport_sample()); + ac->set_value (ac->normal (), PBD::Controllable::UseGroup); + } + return; + } +# endif + if (shift_mod ()) { ToggleStripableSelection (s); } else { @@ -1697,8 +1782,8 @@ FaderPort8::notify_fader_mode_changed () ARMButtonChange (false); break; } - assign_strips (false); - notify_automation_mode_changed (); + assign_strips (); + notify_route_state_changed (); } void @@ -1711,7 +1796,7 @@ FaderPort8::notify_stripable_added_or_removed () * - Properties::hidden * - Properties::order */ - assign_strips (false); + assign_strips (); } /* called from static PresentationInfo::Change */ @@ -1751,7 +1836,11 @@ FaderPort8::notify_stripable_property_changed (boost::weak_ptr ws, co uint8_t id = _assigned_strips[s]; if (what_changed.contains (Properties::color)) { - _ctrls.strip(id).select_button ().set_color (s->presentation_info ().color()); + _ctrls.strip(id).set_select_button_color (s->presentation_info ().color()); + } + + if (what_changed.empty ()) { + _ctrls.strip(id).set_stripable (s, _ctrls.fader_mode() == ModePan); } if (what_changed.contains (Properties::name)) { @@ -1770,6 +1859,20 @@ FaderPort8::notify_stripable_property_changed (boost::weak_ptr ws, co } } +#ifdef FADERPORT2 +void +FaderPort8::stripable_selection_changed () +{ + if (!_device_active || _chan_locked) { + return; + } + route_state_connections.drop_connections (); + assign_stripables (false); + subscribe_to_strip_signals (); +} + +#else + void FaderPort8::stripable_selection_changed () { @@ -1779,7 +1882,7 @@ FaderPort8::stripable_selection_changed () */ return; } - automation_state_connections.drop_connections(); + route_state_connections.drop_connections(); switch (_ctrls.fader_mode ()) { case ModePlugins: @@ -1788,6 +1891,9 @@ FaderPort8::stripable_selection_changed () int wk = _showing_well_known; drop_ctrl_connections (); select_plugin (wk); + } else if (_proc_params.size() == 0) { + /* selecting plugin, update available */ + spill_plugins (); } return; case ModeSend: @@ -1808,21 +1914,34 @@ FaderPort8::stripable_selection_changed () _ctrls.strip(id).select_button ().set_blinking (sel && s == first_selected_stripable ()); } - /* track automation-mode of primary selection */ + subscribe_to_strip_signals (); +} +#endif + +void +FaderPort8::subscribe_to_strip_signals () +{ + /* keep track of automation-mode of primary selection, shared buttons */ boost::shared_ptr s = first_selected_stripable(); if (s) { boost::shared_ptr ac; ac = s->gain_control(); if (ac && ac->alist()) { - ac->alist()->automation_state_changed.connect (automation_state_connections, MISSING_INVALIDATOR, boost::bind (&FaderPort8::notify_automation_mode_changed, this), this); + ac->alist()->automation_state_changed.connect (route_state_connections, MISSING_INVALIDATOR, boost::bind (&FaderPort8::notify_route_state_changed, this), this); } ac = s->pan_azimuth_control(); if (ac && ac->alist()) { - ac->alist()->automation_state_changed.connect (automation_state_connections, MISSING_INVALIDATOR, boost::bind (&FaderPort8::notify_automation_mode_changed, this), this); + ac->alist()->automation_state_changed.connect (route_state_connections, MISSING_INVALIDATOR, boost::bind (&FaderPort8::notify_route_state_changed, this), this); } +#ifdef FADERPORT2 + ac = s->rec_enable_control(); + if (ac) { + ac->Changed.connect (route_state_connections, MISSING_INVALIDATOR, boost::bind (&FaderPort8::notify_route_state_changed, this), this); + } +#endif } /* set lights */ - notify_automation_mode_changed (); + notify_route_state_changed (); } @@ -1847,16 +1966,18 @@ FaderPort8::move_selected_into_view () } int off = std::distance (strips.begin(), it); - if (_channel_off <= off && off < _channel_off + 8) { + int channel_off = get_channel_off (_ctrls.mix_mode ()); + if (channel_off <= off && off < channel_off + N_STRIPS) { return; } - if (_channel_off > off) { - _channel_off = off; + if (channel_off > off) { + channel_off = off; } else { - _channel_off = off - 7; + channel_off = off - (N_STRIPS - 1); } - assign_strips (false); + set_channel_off (_ctrls.mix_mode (), channel_off); + assign_strips (); } void @@ -1905,18 +2026,24 @@ FaderPort8::select_prev_next (bool next) void FaderPort8::bank (bool down, bool page) { - int dt = page ? 8 : 1; +#ifdef FADERPORT2 + // XXX this should preferably be in actions.cc + AccessAction ("Editor", down ? "select-prev-stripable" : "select-next-stripable"); + return; +#endif + + int dt = page ? N_STRIPS : 1; if (down) { dt *= -1; } - _channel_off += dt; - assign_strips (false); + set_channel_off (_ctrls.mix_mode (), get_channel_off (_ctrls.mix_mode ()) + dt); + assign_strips (); } void FaderPort8::bank_param (bool down, bool page) { - int dt = page ? 8 : 1; + int dt = page ? N_STRIPS : 1; if (down) { dt *= -1; }