From 05d35395916f6d00f230ddd64ee0abbea3b5a09c Mon Sep 17 00:00:00 2001 From: Jan Lentfer Date: Fri, 21 Sep 2018 16:06:16 +0200 Subject: [PATCH] LCXL: complete overhaul and Mixbus support --- .../surfaces/launch_control_xl/controllers.cc | 1232 ++++++++++++++--- .../launch_control_xl/launch_control_xl.cc | 714 ++++++++-- .../launch_control_xl/launch_control_xl.h | 287 ++-- 3 files changed, 1805 insertions(+), 428 deletions(-) diff --git a/libs/surfaces/launch_control_xl/controllers.cc b/libs/surfaces/launch_control_xl/controllers.cc index eca0f7b7d7..37c048034f 100644 --- a/libs/surfaces/launch_control_xl/controllers.cc +++ b/libs/surfaces/launch_control_xl/controllers.cc @@ -34,44 +34,170 @@ using std::cerr; void LaunchControlXL::build_maps () { - /* Knobs */ + cc_knob_map.clear(); + id_knob_map.clear(); + cc_fader_map.clear(); + id_fader_map.clear(); + nn_note_button_map.clear(); + id_note_button_map.clear(); + cc_controller_button_map.clear(); + id_controller_button_map.clear(); + /* Knobs */ boost::shared_ptr knob; - #define MAKE_KNOB(i,cc,index,a) \ - knob.reset (new Knob ((i), (cc), (index), (a), (*this))); \ + #define MAKE_KNOB(i,cc,index,c_on,c_off,a) \ + knob.reset (new Knob ((i), (cc), (index), (c_on), (c_off), (a), (*this))); \ cc_knob_map.insert (std::make_pair (knob->controller_number(), knob)); \ - id_knob_map.insert (std::make_pair (knob->id(), knob)) + id_knob_map.insert (std::make_pair (knob->id(), knob)); + #define MAKE_DM_KNOB(i,cc,index,c_on,c_off,action,check) \ + knob.reset (new Knob ((i), (cc), (index), (c_on), (c_off), (action), (check), (*this))); \ + cc_knob_map.insert (std::make_pair (knob->controller_number(), knob)); \ + id_knob_map.insert (std::make_pair (knob->id(), knob)); - MAKE_KNOB (SendA1, 13, 0, &LaunchControlXL::knob_sendA1); - MAKE_KNOB (SendA2, 14, 1, &LaunchControlXL::knob_sendA2); - MAKE_KNOB (SendA3, 15, 2, &LaunchControlXL::knob_sendA3); - MAKE_KNOB (SendA4, 16, 3, &LaunchControlXL::knob_sendA4); - MAKE_KNOB (SendA5, 17, 4, &LaunchControlXL::knob_sendA5); - MAKE_KNOB (SendA6, 18, 5, &LaunchControlXL::knob_sendA6); - MAKE_KNOB (SendA7, 19, 6, &LaunchControlXL::knob_sendA7); - MAKE_KNOB (SendA8, 20, 7, &LaunchControlXL::knob_sendA8); + if (!device_mode()) { /* mixer mode */ + MAKE_KNOB (SendA1, 13, 0, RedFull, RedLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 0))); + MAKE_KNOB (SendA2, 14, 1, YellowFull, YellowLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 1))); + MAKE_KNOB (SendA3, 15, 2, GreenFull, GreenLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 2))); + MAKE_KNOB (SendA4, 16, 3, AmberFull, AmberLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 3))); + MAKE_KNOB (SendA5, 17, 4, RedFull, RedLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 4))); + MAKE_KNOB (SendA6, 18, 5, YellowFull, YellowLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 5))); + MAKE_KNOB (SendA7, 19, 6, GreenFull, GreenLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 6))); + MAKE_KNOB (SendA8, 20, 7, AmberFull, AmberLow, boost::function (boost::bind (&LaunchControlXL::knob_sendA, this, 7))); - MAKE_KNOB (SendB1, 29, 8, &LaunchControlXL::knob_sendB1); - MAKE_KNOB (SendB2, 30, 9, &LaunchControlXL::knob_sendB2); - MAKE_KNOB (SendB3, 31, 10, &LaunchControlXL::knob_sendB3); - MAKE_KNOB (SendB4, 32, 11, &LaunchControlXL::knob_sendB4); - MAKE_KNOB (SendB5, 33, 12, &LaunchControlXL::knob_sendB5); - MAKE_KNOB (SendB6, 34, 13, &LaunchControlXL::knob_sendB6); - MAKE_KNOB (SendB7, 35, 14, &LaunchControlXL::knob_sendB7); - MAKE_KNOB (SendB8, 36, 15, &LaunchControlXL::knob_sendB8); + MAKE_KNOB (SendB1, 29, 8, RedFull, RedLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 0))); + MAKE_KNOB (SendB2, 30, 9, YellowFull, YellowLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 1))); + MAKE_KNOB (SendB3, 31, 10, GreenFull, GreenLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 2))); + MAKE_KNOB (SendB4, 32, 11, AmberFull, AmberLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 3))); + MAKE_KNOB (SendB5, 33, 12, RedFull, RedLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 4))); + MAKE_KNOB (SendB6, 34, 13, YellowFull, YellowLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 5))); + MAKE_KNOB (SendB7, 35, 14, GreenFull, GreenLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 6))); + MAKE_KNOB (SendB8, 36, 15, AmberFull, AmberLow, boost::function (boost::bind (&LaunchControlXL::knob_sendB, this, 7))); + + MAKE_KNOB (Pan1, 49, 16, RedFull, RedLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 0))); + MAKE_KNOB (Pan2, 50, 17, YellowFull, YellowLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 1))); + MAKE_KNOB (Pan3, 51, 18, GreenFull, GreenLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 2))); + MAKE_KNOB (Pan4, 52, 19, AmberFull, AmberLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 3))); + MAKE_KNOB (Pan5, 53, 20, RedFull, RedLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 4))); + MAKE_KNOB (Pan6, 54, 21, YellowFull, YellowLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 5))); + MAKE_KNOB (Pan7, 55, 22, GreenFull, GreenLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 6))); + MAKE_KNOB (Pan8, 56, 23, AmberFull, AmberLow, boost::function (boost::bind (&LaunchControlXL::knob_pan, this, 7))); + + } else { /* device mode */ + +#ifdef MIXBUS // from here Mixbus Standard + 32C + MAKE_DM_KNOB (SendB5, 33, 12, RedFull, RedLow, boost::function + (boost::bind (&LaunchControlXL::dm_trim, this, SendB5)), + boost::bind(&LaunchControlXL::dm_check_trim, this)); + MAKE_DM_KNOB (SendB6, 34, 13, GreenFull, GreenLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_comp, this, SendB6, CompMakeup)), + boost::bind(&LaunchControlXL::dm_mb_comp_enabled,this)); + MAKE_DM_KNOB (SendB7, 35, 14, GreenFull, GreenLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_comp, this, SendB7, CompSpeed)), + boost::bind(&LaunchControlXL::dm_mb_comp_enabled, this)); + MAKE_DM_KNOB (SendB8, 36, 15, GreenFull, GreenLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_comp, this, SendB8, CompMode)), + boost::bind(&LaunchControlXL::dm_mb_comp_enabled, this)); + + /* Pan Knobs -> Sends */ + for (uint8_t i = 0; i < 8; ++i) { + MAKE_DM_KNOB (static_cast(i + 16), (i + 49), (i + 16), GreenLow, YellowLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_sends, this, static_cast(i + 16))), + boost::function (boost::bind(&LaunchControlXL::dm_mb_check_send_knob, this, static_cast(i + 16)))); + } + +#ifdef MIXBUS32C // from here 32C only + + if (first_selected_stripable() && (first_selected_stripable()->is_master() || first_selected_stripable()->mixbus())) { + MAKE_DM_KNOB (SendA1, 13, 0, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA1, true, 0)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 0))); + MAKE_DM_KNOB (SendA2, 14, 1, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA2, true, 1)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 1))); + MAKE_DM_KNOB (SendA3, 15, 2, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA3, true, 2)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 2))); + MAKE_DM_KNOB (SendA6, 18, 5, RedLow, RedLow, boost::function + (boost::bind (&LaunchControlXL::dm_pan_width, this, SendA6)), + boost::bind(&LaunchControlXL::dm_check_pan_width, this)); + MAKE_DM_KNOB (SendA7, 19, 6, AmberLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_tapedrive, this, SendA7)), + boost::bind(&LaunchControlXL::dm_mb_has_tapedrive, this)); + } else { + MAKE_DM_KNOB (SendA1, 13, 0, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA1, false, 0)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); + MAKE_DM_KNOB (SendA2, 14, 1, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA2, true, 0)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 0))); + MAKE_DM_KNOB (SendA3, 15, 2, YellowLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA3, false, 1)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); + MAKE_DM_KNOB (SendA4, 16, 3, YellowLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA4, true, 1)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 1))); + MAKE_DM_KNOB (SendA5, 17, 4, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA5, false, 2)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); + MAKE_DM_KNOB (SendA6, 18, 5, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA6, true, 2)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 2))); + MAKE_DM_KNOB (SendA7, 19, 6, YellowLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA7, false, 3)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); + MAKE_DM_KNOB (SendA8, 20, 7, YellowLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA8, true, 3)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 3))); + } + MAKE_DM_KNOB (SendB1, 29, 8, YellowFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_flt_frq, this, SendB1, true)), + boost::bind(&LaunchControlXL::dm_mb_flt_enabled, this)); + MAKE_DM_KNOB (SendB2, 30, 9, YellowFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_flt_frq, this, SendB2, false)), + boost::bind(&LaunchControlXL::dm_mb_flt_enabled, this)); + MAKE_DM_KNOB (SendB4, 32, 11, RedLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_pan_azi, this, SendB4)), + boost::bind(&LaunchControlXL::dm_check_pan_azi, this)); + +#else // from here Mixbus Standard only + MAKE_DM_KNOB (SendA1, 13, 0, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA1, true, 0)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 0))); + MAKE_DM_KNOB (SendA2, 14, 1, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA2, true, 1)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 1))); + MAKE_DM_KNOB (SendA3, 15, 2, AmberFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendA3, true, 2)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 2))); + MAKE_DM_KNOB (SendA5, 17, 4, RedLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_pan_azi, this, SendA5)), + boost::bind(&LaunchControlXL::dm_check_pan_azi, this)); + MAKE_DM_KNOB (SendA6, 18, 5, RedLow, RedLow, boost::function + (boost::bind (&LaunchControlXL::dm_pan_width, this, SendA6)), + boost::bind(&LaunchControlXL::dm_check_pan_width, this)); + MAKE_DM_KNOB (SendA7, 19, 6, AmberLow, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_tapedrive, this, SendA7)), + boost::bind(&LaunchControlXL::dm_mb_has_tapedrive, this)); + MAKE_DM_KNOB (SendB1, 29, 8, YellowFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendB1, false, 0)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); + MAKE_DM_KNOB (SendB2, 30, 9, YellowFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendB2, false, 1)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); + MAKE_DM_KNOB (SendB3, 31, 10, YellowFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_eq, this, SendB3, false, 2)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); + MAKE_DM_KNOB (SendB4, 32, 11, YellowFull, AmberLow, boost::function + (boost::bind (&LaunchControlXL::dm_mb_flt_frq, this, SendB4, true)), + boost::bind(&LaunchControlXL::dm_mb_eq_freq_enabled, this)); +#endif +#else // from here Ardour +#endif + } - MAKE_KNOB (Pan1, 49, 16, &LaunchControlXL::knob_pan1); - MAKE_KNOB (Pan2, 50, 17, &LaunchControlXL::knob_pan2); - MAKE_KNOB (Pan3, 51, 18, &LaunchControlXL::knob_pan3); - MAKE_KNOB (Pan4, 52, 19, &LaunchControlXL::knob_pan4); - MAKE_KNOB (Pan5, 53, 20, &LaunchControlXL::knob_pan5); - MAKE_KNOB (Pan6, 54, 21, &LaunchControlXL::knob_pan6); - MAKE_KNOB (Pan7, 55, 22, &LaunchControlXL::knob_pan7); - MAKE_KNOB (Pan8, 56, 23, &LaunchControlXL::knob_pan8); /* Faders */ - boost::shared_ptr fader; #define MAKE_FADER(i,cc,a) \ @@ -79,32 +205,44 @@ LaunchControlXL::build_maps () cc_fader_map.insert (std::make_pair (fader->controller_number(), fader)); \ id_fader_map.insert (std::make_pair (fader->id(), fader)) - MAKE_FADER (Fader1, 77, &LaunchControlXL::fader_1); - MAKE_FADER (Fader2, 78, &LaunchControlXL::fader_2); - MAKE_FADER (Fader3, 79, &LaunchControlXL::fader_3); - MAKE_FADER (Fader4, 80, &LaunchControlXL::fader_4); - MAKE_FADER (Fader5, 81, &LaunchControlXL::fader_5); - MAKE_FADER (Fader6, 82, &LaunchControlXL::fader_6); - MAKE_FADER (Fader7, 83, &LaunchControlXL::fader_7); - MAKE_FADER (Fader8, 84, &LaunchControlXL::fader_8); + if (!device_mode()) { /* mix mode */ + for (uint8_t i = 0; i < 8; ++i) { + MAKE_FADER(static_cast(i), i+77, boost::function + (boost::bind (&LaunchControlXL::fader, this, i))); + } + } else { /* device mode */ + MAKE_FADER(Fader1, 77, boost::function + (boost::bind (&LaunchControlXL::dm_fader, this, Fader1))); +#ifdef MIXBUS + MAKE_FADER(Fader2, 78, boost::function + (boost::bind (&LaunchControlXL::dm_mb_comp_thresh, this, Fader2))); +#endif + } /* Buttons */ - boost::shared_ptr controller_button; boost::shared_ptr note_button; - #define MAKE_TRACK_BUTTON_PRESS(i,nn,index,color,p) \ - note_button.reset (new TrackButton ((i), (nn), (index), (color), (p), (*this))); \ + #define MAKE_TRACK_BUTTON_PRESS(i,nn,index,c_on,c_off,p,check) \ + note_button.reset (new TrackButton ((i), (nn), (index), (c_on), (c_off), (p), \ + boost::bind(&LaunchControlXL::relax, this), boost::bind(&LaunchControlXL::relax, this), (check), (*this))); \ + nn_note_button_map.insert (std::make_pair (note_button->note_number(), note_button)); \ + id_note_button_map.insert (std::make_pair (note_button->id(), note_button)) + #define MAKE_CTRL_BUTTON_PRESS(i,nn,index,c_on,c_off,p,check) \ + note_button.reset (new TrackButton ((i), (nn), (index), (c_on), (c_off), (p), \ + boost::bind(&LaunchControlXL::relax, this), boost::bind(&LaunchControlXL::relax, this), (check), (*this))); \ nn_note_button_map.insert (std::make_pair (note_button->note_number(), note_button)); \ id_note_button_map.insert (std::make_pair (note_button->id(), note_button)) #define MAKE_SELECT_BUTTON_PRESS(i,cc,index,p) \ - controller_button.reset (new SelectButton ((i), (cc), (index), (p), (*this))); \ + controller_button.reset (new SelectButton ((i), (cc), (index), (p), \ + boost::bind(&LaunchControlXL::relax, this), boost::bind(&LaunchControlXL::relax, this), (*this))); \ cc_controller_button_map.insert (std::make_pair (controller_button->controller_number(), controller_button)); \ id_controller_button_map.insert (std::make_pair (controller_button->id(), controller_button)) #define MAKE_TRACK_STATE_BUTTON_PRESS(i,nn,index,p) \ - note_button.reset (new TrackStateButton ((i), (nn), (index), (p), (*this))); \ + note_button.reset (new TrackStateButton ((i), (nn), (index), (p), \ + boost::bind(&LaunchControlXL::relax, this), boost::bind(&LaunchControlXL::relax, this), (*this))); \ nn_note_button_map.insert (std::make_pair (note_button->note_number(), note_button)); \ id_note_button_map.insert (std::make_pair (note_button->id(), note_button)) #define MAKE_TRACK_STATE_BUTTON_PRESS_RELEASE_LONG(i,nn,index, p,r,l) \ @@ -112,34 +250,124 @@ LaunchControlXL::build_maps () nn_note_button_map.insert (std::make_pair (note_button->note_number(), note_button)); \ id_note_button_map.insert (std::make_pair (note_button->id(), note_button)) + /* Track Focus Buttons */ + if (!device_mode()) { /* mixer mode */ + for (uint8_t i = 0; i < 4; ++i) { + MAKE_TRACK_BUTTON_PRESS(static_cast(i), i+41, i+24, YellowFull, YellowLow, + boost::function (boost::bind (&LaunchControlXL::button_track_focus, this, i)), + boost::function (boost::bind (&LaunchControlXL::dm_check_dummy, this, dev_nonexistant))); + } - MAKE_TRACK_BUTTON_PRESS(Focus1, 41, 24, YellowLow, &LaunchControlXL::button_track_focus_1); - MAKE_TRACK_BUTTON_PRESS(Focus2, 42, 25, YellowLow, &LaunchControlXL::button_track_focus_2); - MAKE_TRACK_BUTTON_PRESS(Focus3, 43, 26, YellowLow, &LaunchControlXL::button_track_focus_3); - MAKE_TRACK_BUTTON_PRESS(Focus4, 44, 27, YellowLow, &LaunchControlXL::button_track_focus_4); - MAKE_TRACK_BUTTON_PRESS(Focus5, 57, 28, YellowLow, &LaunchControlXL::button_track_focus_5); - MAKE_TRACK_BUTTON_PRESS(Focus6, 58, 29, YellowLow, &LaunchControlXL::button_track_focus_6); - MAKE_TRACK_BUTTON_PRESS(Focus7, 59, 30, YellowLow, &LaunchControlXL::button_track_focus_7); - MAKE_TRACK_BUTTON_PRESS(Focus8, 60, 31, YellowLow, &LaunchControlXL::button_track_focus_8); - MAKE_TRACK_BUTTON_PRESS(Control1, 73, 32, AmberLow, &LaunchControlXL::button_track_control_1); - MAKE_TRACK_BUTTON_PRESS(Control2, 74, 33, AmberLow, &LaunchControlXL::button_track_control_2); - MAKE_TRACK_BUTTON_PRESS(Control3, 75, 34, AmberLow, &LaunchControlXL::button_track_control_3); - MAKE_TRACK_BUTTON_PRESS(Control4, 76, 35, AmberLow, &LaunchControlXL::button_track_control_4); - MAKE_TRACK_BUTTON_PRESS(Control5, 89, 36, AmberLow, &LaunchControlXL::button_track_control_5); - MAKE_TRACK_BUTTON_PRESS(Control6, 90, 37, AmberLow, &LaunchControlXL::button_track_control_6); - MAKE_TRACK_BUTTON_PRESS(Control7, 91, 38, AmberLow, &LaunchControlXL::button_track_control_7); - MAKE_TRACK_BUTTON_PRESS(Control8, 92, 39, AmberLow, &LaunchControlXL::button_track_control_8); + for (uint8_t i = 0; i < 4; ++i) { + MAKE_TRACK_BUTTON_PRESS(static_cast(i+4), i+57, i+28, YellowFull, YellowLow, + boost::function (boost::bind (&LaunchControlXL::button_track_focus, this, i+4)), + boost::function (boost::bind (&LaunchControlXL::dm_check_dummy, this, dev_nonexistant))); + } - MAKE_SELECT_BUTTON_PRESS(SelectUp, 104, 44, &LaunchControlXL::button_select_up); - MAKE_SELECT_BUTTON_PRESS(SelectDown, 105, 45, &LaunchControlXL::button_select_down); - MAKE_SELECT_BUTTON_PRESS(SelectLeft, 106, 46, &LaunchControlXL::button_select_left); - MAKE_SELECT_BUTTON_PRESS(SelectRight, 107, 47, &LaunchControlXL::button_select_right); + } else { /* device mode */ +#ifdef MIXBUS + for (uint8_t i = 0; i < 4; ++i) { + MAKE_TRACK_BUTTON_PRESS(static_cast(i), i+41, i+24, GreenFull, YellowLow, + boost::function (boost::bind (&LaunchControlXL::dm_mb_send_switch, this, static_cast(i))), + boost::function (boost::bind (&LaunchControlXL::dm_mb_check_send_button, this, i))); - MAKE_TRACK_STATE_BUTTON_PRESS_RELEASE_LONG(Device, 105, 40, &LaunchControlXL::relax, &LaunchControlXL::button_device, &LaunchControlXL::button_device_long_press);; - MAKE_TRACK_STATE_BUTTON_PRESS(Mute, 106, 41, &LaunchControlXL::button_mute); - MAKE_TRACK_STATE_BUTTON_PRESS(Solo, 107, 42, &LaunchControlXL::button_solo); - MAKE_TRACK_STATE_BUTTON_PRESS(Record, 108, 43, &LaunchControlXL::button_record); + } + for (uint8_t i = 0; i < 4; ++i) { + MAKE_TRACK_BUTTON_PRESS(static_cast(i+4), i+57, i+28, GreenFull, YellowLow, + boost::function (boost::bind (&LaunchControlXL::dm_mb_send_switch, this, static_cast(i+4))), + boost::function (boost::bind (&LaunchControlXL::dm_mb_check_send_button, this, i+4))); + } +#endif + } + /* Track Control Buttons */ + if (!device_mode()) { /* mixer mode */ + /* Control Buttons in mix mode change their color dynamically so we won't set them here */ + for (uint8_t i = 0; i < 4; ++i) { + MAKE_CTRL_BUTTON_PRESS(static_cast(i+8), i+73, i+32, Off, Off, + boost::function (boost::bind (&LaunchControlXL::button_press_track_control, this, i)), + boost::function (boost::bind (&LaunchControlXL::dm_check_dummy, this, dev_nonexistant))); + } + + for (uint8_t i = 0; i < 4; ++i) { + MAKE_CTRL_BUTTON_PRESS(static_cast(i+12), i+89, i+36, Off, Off, + boost::function (boost::bind (&LaunchControlXL::button_press_track_control, this, i+4)), + boost::function (boost::bind (&LaunchControlXL::dm_check_dummy, this, dev_nonexistant))); + } + + } else { /*device mode */ +#ifdef MIXBUS // from here Mixbus Standard + 32C + MAKE_CTRL_BUTTON_PRESS(Control1, 73, 32, YellowFull, YellowLow, (boost::bind (&LaunchControlXL::dm_mute_switch, this)), + boost::bind (&LaunchControlXL::dm_mute_enabled, this)); + MAKE_CTRL_BUTTON_PRESS(Control2, 74, 33, GreenFull, GreenLow, (boost::bind (&LaunchControlXL::dm_solo_switch, this)), + boost::bind (&LaunchControlXL::dm_solo_enabled, this)); + MAKE_CTRL_BUTTON_PRESS(Control3, 75, 34, AmberFull, AmberLow, (boost::bind (&LaunchControlXL::dm_mb_eq_switch, this)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_gain_enabled, this, 0))); + + +#ifdef MIXBUS32C // from here 32C only + MAKE_CTRL_BUTTON_PRESS(Control4, 76, 35, AmberFull, AmberLow, + boost::function (boost::bind (&LaunchControlXL::dm_mb_eq_shape_switch, this, 0)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_shape_enabled, this, 0 ))); + MAKE_CTRL_BUTTON_PRESS(Control5, 89, 36, AmberFull, AmberLow, + boost::function (boost::bind (&LaunchControlXL::dm_mb_eq_shape_switch, this, 3)), + boost::function (boost::bind(&LaunchControlXL::dm_mb_eq_shape_enabled, this, 3 ))); + MAKE_CTRL_BUTTON_PRESS(Control6, 90, 37, YellowFull, YellowLow, (boost::bind (&LaunchControlXL::dm_mb_flt_switch, this)), + boost::bind(&LaunchControlXL::dm_mb_flt_enabled, this)); + MAKE_CTRL_BUTTON_PRESS(Control7, 91, 38, GreenFull, GreenLow, (boost::bind (&LaunchControlXL::dm_mb_master_assign_switch, this)), + boost::bind(&LaunchControlXL::dm_mb_master_assign_enabled, this)); + MAKE_CTRL_BUTTON_PRESS(Control8, 92, 39, GreenFull, GreenLow, (boost::bind (&LaunchControlXL::dm_mb_comp_switch, this)), + boost::bind(&LaunchControlXL::dm_mb_comp_enabled, this)); + +#else // from here Mixbus Standard only + MAKE_CTRL_BUTTON_PRESS(Control5, 89, 36, GreenFull, GreenLow, (boost::bind (&LaunchControlXL::dm_mb_master_assign_switch, this)), + boost::bind(&LaunchControlXL::dm_mb_master_assign_enabled, this)); + MAKE_CTRL_BUTTON_PRESS(Control7, 91, 38, GreenFull, GreenLow, (boost::bind (&LaunchControlXL::dm_mb_comp_switch, this)), + boost::bind(&LaunchControlXL::dm_mb_comp_enabled, this)); + MAKE_CTRL_BUTTON_PRESS(Control8, 92, 39, RedFull, RedLow, (boost::bind (&LaunchControlXL::dm_recenable_switch, this)), + boost::bind(&LaunchControlXL::dm_recenable_enabled, this)); + +#endif +#else // Ardour +#endif + } + + /* Select and Mode Buttons on the right side */ + + /* Sends Select buttons are independent of mode */ + MAKE_SELECT_BUTTON_PRESS(SelectUp, 104, 44, boost::function (boost::bind (&LaunchControlXL::send_bank_switch, this, false))); + MAKE_SELECT_BUTTON_PRESS(SelectDown, 105, 45, boost::function (boost::bind (&LaunchControlXL::send_bank_switch, this, true))); + + /* Device Button needs to be always there */ + MAKE_TRACK_STATE_BUTTON_PRESS_RELEASE_LONG(Device, 105, 40, + boost::bind (&LaunchControlXL::relax, this) , + boost::bind (&LaunchControlXL::button_device, this), + boost::bind (&LaunchControlXL::button_device_long_press, this)); + + + if (!device_mode()) { /* mixer mode */ + MAKE_SELECT_BUTTON_PRESS(SelectLeft, 106, 46, boost::bind (&LaunchControlXL::button_select_left, this)); + MAKE_SELECT_BUTTON_PRESS(SelectRight, 107, 47, boost::bind (&LaunchControlXL::button_select_right, this)); + + //MAKE_TRACK_STATE_BUTTON_PRESS(Mute, 106, 41, boost::bind (&LaunchControlXL::button_mute, this)); + + MAKE_TRACK_STATE_BUTTON_PRESS_RELEASE_LONG(Mute, 106, 41, + boost::bind (&LaunchControlXL::relax, this) , + boost::bind (&LaunchControlXL::button_mute, this), + boost::bind (&LaunchControlXL::button_mute_long_press, this)); + + MAKE_TRACK_STATE_BUTTON_PRESS_RELEASE_LONG(Solo, 107, 42, + boost::bind (&LaunchControlXL::relax, this) , + boost::bind (&LaunchControlXL::button_solo, this), + boost::bind (&LaunchControlXL::button_solo_long_press, this)); + + //MAKE_TRACK_STATE_BUTTON_PRESS(Solo, 107, 42, boost::bind (&LaunchControlXL::button_solo, this)); + MAKE_TRACK_STATE_BUTTON_PRESS(Record, 108, 43, boost::bind (&LaunchControlXL::button_record, this)); + + } else { /* device mode */ + MAKE_SELECT_BUTTON_PRESS(SelectLeft, 106, 46, boost::bind (&LaunchControlXL::dm_select_prev_strip, this)); + MAKE_SELECT_BUTTON_PRESS(SelectRight, 107, 47, boost::bind (&LaunchControlXL::dm_select_next_strip, this)); + } } std::string @@ -349,77 +577,63 @@ LaunchControlXL::get_ac_by_state(uint8_t n) { return ac; } +boost::shared_ptr +LaunchControlXL::knob_by_id(KnobID id) +{ + IDKnobMap::iterator k = id_knob_map.find(id); + return boost::dynamic_pointer_cast (k->second); + +} + boost::shared_ptr* LaunchControlXL::knobs_by_column(uint8_t col, boost::shared_ptr* knob_col) { for (uint8_t n = 0; n < 3; ++n) { - knob_col[n] = id_knob_map.find(static_cast(col+n*8))->second; + if (id_knob_map.find(static_cast(col+n*8)) != id_knob_map.end()) { + knob_col[n] = id_knob_map.find(static_cast(col+n*8))->second; + } } return knob_col; } void -LaunchControlXL::update_knob_led(uint8_t n) +LaunchControlXL::update_knob_led_by_id (uint8_t id, LEDColor color) +{ + + boost::shared_ptr knob = 0; + IDKnobMap::iterator k = id_knob_map.find(static_cast(id)); + + if (k != id_knob_map.end()) { + knob = k->second; + } + + knob->set_color(color); + write (knob->state_msg()); +} + +void +LaunchControlXL::update_knob_led_by_strip(uint8_t n) { LEDColor color; - uint32_t absolute_strip_num = (n + bank_start) % 8; - - if (stripable[n]) { - switch (absolute_strip_num) { - case 0: - case 4: - if (stripable[n]->is_selected()) { - color = RedFull; - } else { - color = RedLow; - } - break; - - case 1: - case 5: - if (stripable[n]->is_selected()) { - color = YellowFull; - } else { - color = YellowLow; - } - break; - - case 2: - case 6: - if (stripable[n]->is_selected()) { - color = GreenFull; - } else { - color = GreenLow; - } - break; - - case 3: - case 7: - if (stripable[n]->is_master()) { - color = RedFull; - } else { - if (stripable[n]->is_selected()) { - color = AmberFull; - } else { - color = AmberLow; - } - } - } - } - boost::shared_ptr knobs_col[3]; knobs_by_column(n, knobs_col); - for (uint8_t s = 0; s < 3; ++s) - { - if (stripable[n]) { - knobs_col[s]->set_color(color); - } else { - knobs_col[s]->set_color(Off); + for (uint8_t s = 0; s < 3; ++s) { + if (knobs_col[s]) { + if (stripable[n]) { + if (stripable[n]->is_selected()) { + color = knobs_col[s]->color_enabled(); + } else { + color = knobs_col[s]->color_disabled(); + } + knobs_col[s]->set_color(color); + } else { + knobs_col[s]->set_color(Off); + } + write (knobs_col[s]->state_msg()); } - write (knobs_col[s]->state_msg()); } } @@ -432,43 +646,22 @@ LaunchControlXL::update_track_control_led(uint8_t n) return; } + if ((buttons_down.find(Device) != buttons_down.end())) { + /* Don't update LEDs if Device button is hold - we are working on selected strips */ + return; + } + if (stripable[n]) { - boost::shared_ptr ac = get_ac_by_state(n); - - switch(track_mode()) { - case TrackMute: + boost::shared_ptr ac = get_ac_by_state(n); + if (ac) { if (ac->get_value()) { - b->set_color(YellowFull); + b->set_color(b->color_enabled()); } else { - b->set_color(AmberLow); + b->set_color(b->color_disabled()); } - break; - case TrackSolo: - if (ac && !(stripable[n]->is_master())) { - if (ac->get_value()) { - b->set_color(GreenFull); - } else { - b->set_color(GreenLow); - } - } else { - b->set_color(Off); - } - break; - case TrackRecord: - if (ac) { - if (ac->get_value()) { - b->set_color(RedFull); - } else { - b->set_color(RedLow); - } - } else { - b->set_color(Off); - } - break; - - default: - break; - } + } else { + b->set_color(Off); + } } else { b->set_color(Off); } @@ -481,7 +674,8 @@ LaunchControlXL::solo_mute_rec_changed(uint32_t n) { if (!stripable[n]) { return; } - update_track_control_led(n); + switch_bank(bank_start); + //update_track_control_led(n); } void @@ -497,6 +691,8 @@ LaunchControlXL::solo_iso_changed(uint32_t n) void LaunchControlXL::solo_iso_led_bank () { + if (device_mode()) { return; } + int stripable_counter = get_amount_of_tracks(); if (!(buttons_down.find(Device) != buttons_down.end())) { @@ -510,7 +706,9 @@ LaunchControlXL::solo_iso_led_bank () } else { b->set_color(Off); } - write (b->state_msg()); + if (b) { + write (b->state_msg()); + } } } LaunchControlXL::set_refresh_leds_flag(true); @@ -526,12 +724,13 @@ LaunchControlXL::master_send_changed(uint32_t n) } else { master_send_led_bank(); } - } void LaunchControlXL::master_send_led_bank () { + if (device_mode()) { return; } + if (!(buttons_down.find(Device) != buttons_down.end())) { return; } else { @@ -546,7 +745,9 @@ LaunchControlXL::master_send_led_bank () b->set_color(Off); } } - write (b->state_msg()); + if (b) { + write (b->state_msg()); + } } LaunchControlXL::set_refresh_leds_flag(true); } @@ -600,7 +801,7 @@ LaunchControlXL::knob_sendA(uint8_t n) if (buttons_down.find(Device) != buttons_down.end()) { // Device button hold ac = stripable[n]->trim_control(); } else { - ac = stripable[n]->send_level_controllable (0); + ac = stripable[n]->send_level_controllable (send_bank_base()); } if (ac && check_pick_up(knob, ac)) { @@ -635,7 +836,7 @@ LaunchControlXL::knob_sendB(uint8_t n) /* something */ #endif } else { - ac = stripable[n]->send_level_controllable (1); + ac = stripable[n]->send_level_controllable (send_bank_base() + 1); } if (ac && check_pick_up(knob, ac)) { @@ -664,15 +865,16 @@ LaunchControlXL::knob_pan(uint8_t n) boost::shared_ptr ac; if (buttons_down.find(Device) != buttons_down.end()) { // Device button hold - #ifdef MIXBUS +#ifdef MIXBUS ac = stripable[n]->comp_threshold_controllable(); - #else +#else ac = stripable[n]->pan_width_control(); - #endif +#endif } else { ac = stripable[n]->pan_azimuth_control(); } + if (ac && check_pick_up(knob, ac)) { ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); } @@ -702,7 +904,7 @@ LaunchControlXL::button_track_focus(uint8_t n) } void -LaunchControlXL::button_track_control(uint8_t n) { +LaunchControlXL::button_press_track_control(uint8_t n) { if (!stripable[n]) { return; } @@ -742,9 +944,11 @@ LaunchControlXL::button_track_mode(TrackMode state) boost::shared_ptr solo = boost::dynamic_pointer_cast (id_note_button_map[Solo]); boost::shared_ptr record = boost::dynamic_pointer_cast (id_note_button_map[Record]); - write(mute->state_msg((state == TrackMute))); - write(solo->state_msg((state == TrackSolo))); - write(record->state_msg((state == TrackRecord))); + if (mute && solo && record) { + write(mute->state_msg((state == TrackMute))); + write(solo->state_msg((state == TrackSolo))); + write(record->state_msg((state == TrackRecord))); + } } void @@ -760,26 +964,29 @@ LaunchControlXL::button_select_right() } void -LaunchControlXL::button_select_up() -{ - -} - -void -LaunchControlXL::button_select_down() -{ - +LaunchControlXL::send_bank_switch(bool down) { + DEBUG_TRACE (DEBUG::LaunchControlXL, string_compose ("send_bank_switch - down: %1\n", down)); + if (down) { + set_send_bank(+2); + } else { + set_send_bank(-2); + } } void LaunchControlXL::button_device() { - +#ifndef MIXBUS + return; // currently device mode only on Mixbus +#endif + LaunchControlXL::set_device_mode(!device_mode()); } void LaunchControlXL::button_device_long_press() { + if (device_mode()) { return ; } + solo_iso_led_bank(); #ifdef MIXBUS master_send_led_bank(); @@ -796,6 +1003,12 @@ LaunchControlXL::button_mute() } } +void +LaunchControlXL::button_mute_long_press() +{ + session->cancel_all_mute(); +} + void LaunchControlXL::button_solo() { @@ -806,6 +1019,12 @@ LaunchControlXL::button_solo() } } +void +LaunchControlXL::button_solo_long_press() +{ + cancel_all_solo(); +} + void LaunchControlXL::button_record() { @@ -821,7 +1040,7 @@ LaunchControlXL::button_long_press_timeout (ButtonID id, boost::shared_ptr*button->long_press_method) (); + (button->long_press_method) (); } else { DEBUG_TRACE (DEBUG::LaunchControlXL, string_compose ("long press timeout for %1, expired/cancelled\n", id)); /* release happened and somehow we were not cancelled */ @@ -839,7 +1058,666 @@ LaunchControlXL::button_long_press_timeout (ButtonID id, boost::shared_ptr button, ButtonID id) { + ButtonID no_timeout_buttons[] = { SelectUp, SelectDown, SelectLeft, SelectRight }; + + for (size_t n = 0; n < sizeof (no_timeout_buttons) / sizeof (no_timeout_buttons[0]); ++n) { + if (id == no_timeout_buttons[n]) { + DEBUG_TRACE (DEBUG::LaunchControlXL, string_compose ("Not using timeout for button id %1\n", id)); + return; + } + } + Glib::RefPtr timeout = Glib::TimeoutSource::create (500); // milliseconds button->timeout_connection = timeout->connect (sigc::bind (sigc::mem_fun (*this, &LaunchControlXL::button_long_press_timeout), id, button)); timeout->attach (main_loop()->get_context()); } + + +/* Device Mode functions */ + +void +LaunchControlXL::dm_select_prev_strip() +{ + access_action ("Editor/select-prev-stripable"); +} + +void +LaunchControlXL::dm_select_next_strip() +{ + access_action ("Editor/select-next-stripable"); +} + +uint8_t +LaunchControlXL::dm_check_dummy (DeviceStatus ds) +{ + return ds; +} + +void +LaunchControlXL::dm_fader (FaderID id) { + + boost::shared_ptr ac; + boost::shared_ptr fader; + + IDFaderMap::iterator f = id_fader_map.find(id); + + if (f != id_fader_map.end()) { + fader = f->second; + } + + ac = first_selected_stripable()->gain_control(); + if (ac && check_pick_up(fader, ac)) { + ac->set_value ( ac->interface_to_internal( fader->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +uint8_t +LaunchControlXL::dm_check_pan_azi() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + if (first_selected_stripable()->pan_azimuth_control()) { + dev_status = dev_active; + } + + return dev_status; +} + +void +LaunchControlXL::dm_pan_azi (KnobID k) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + + ac = first_selected_stripable()->pan_azimuth_control(); + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + + +uint8_t +LaunchControlXL::dm_check_pan_width() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + if (first_selected_stripable()->pan_width_control()) { + dev_status = dev_active; + } + + return dev_status; +} + +void +LaunchControlXL::dm_pan_width (KnobID k) +{ + if (!first_selected_stripable()) { + return; + } + + DEBUG_TRACE (DEBUG::LaunchControlXL, "dm_pan_width()\n"); + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + + ac = first_selected_stripable()->pan_width_control(); + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +uint8_t +LaunchControlXL::dm_check_trim() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + if (first_selected_stripable()->trim_control()) { + dev_status = dev_active; + } + + return dev_status; +} + +void +LaunchControlXL::dm_trim (KnobID k) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + + ac = first_selected_stripable()->trim_control(); + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +uint8_t +LaunchControlXL::dm_mute_enabled() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + if (first_selected_stripable()->mute_control()->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + + return dev_status; +} + +void +LaunchControlXL::dm_mute_switch() +{ + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->mute_control()) { + first_selected_stripable()->mute_control()->set_value(!first_selected_stripable()->mute_control()->get_value(), PBD::Controllable::NoGroup); + } +} + +uint8_t +LaunchControlXL::dm_solo_enabled() +{ + if (!first_selected_stripable() || first_selected_stripable()->is_master()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + if (first_selected_stripable()->solo_control()) { + if (first_selected_stripable()->solo_control()->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + + return dev_status; +} + +void +LaunchControlXL::dm_solo_switch() +{ + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->solo_control()) { + first_selected_stripable()->solo_control()->set_value(!first_selected_stripable()->solo_control()->get_value(), PBD::Controllable::NoGroup); + } +} + +uint8_t +LaunchControlXL::dm_recenable_enabled() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + if (first_selected_stripable()->rec_enable_control()) { + if (first_selected_stripable()->rec_enable_control()->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + + return dev_status; +} + +void +LaunchControlXL::dm_recenable_switch() +{ + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->rec_enable_control()) { + first_selected_stripable()->rec_enable_control()->set_value(!first_selected_stripable()->rec_enable_control()->get_value(), PBD::Controllable::NoGroup); + } +} + + +#ifdef MIXBUS +uint8_t +LaunchControlXL::dm_mb_eq_freq_enabled() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->eq_enable_controllable()) { + if (first_selected_stripable()->eq_enable_controllable()->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + + if (first_selected_stripable()->mixbus() || first_selected_stripable()->is_master()) { + dev_status = dev_nonexistant; + } + + return dev_status; +} + + +uint8_t +LaunchControlXL::dm_mb_eq_gain_enabled(uint8_t band) +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->eq_enable_controllable()) { + if (first_selected_stripable()->eq_enable_controllable()->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + + if (first_selected_stripable()->mixbus() && band > 3) { + dev_status = dev_nonexistant; + } + + return dev_status; +} + +void +LaunchControlXL::dm_mb_eq (KnobID k, bool gain, uint8_t band) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + if (gain) { + ac = first_selected_stripable()->eq_gain_controllable(band); + } else { + ac = first_selected_stripable()->eq_freq_controllable(band); + } + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +void +LaunchControlXL::dm_mb_eq_shape_switch (uint8_t band) +{ + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->eq_shape_controllable(band)) { + first_selected_stripable()->eq_shape_controllable(band)->set_value + (!first_selected_stripable()->eq_shape_controllable(band)->get_value(), PBD::Controllable::NoGroup ); + } +} + + +uint8_t +LaunchControlXL::dm_mb_eq_shape_enabled(uint8_t band) +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->eq_shape_controllable(band)) { + if (first_selected_stripable()->eq_shape_controllable(band)->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + + return dev_status; +} + + +void +LaunchControlXL::dm_mb_eq_switch() +{ + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->eq_enable_controllable()) { + first_selected_stripable()->eq_enable_controllable()->set_value + (!first_selected_stripable()->eq_enable_controllable()->get_value(), PBD::Controllable::NoGroup ); + } +} + +uint8_t +LaunchControlXL::dm_mb_flt_enabled() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + DEBUG_TRACE (DEBUG::LaunchControlXL, "dm_mb_flt_enabled()\n"); + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->filter_enable_controllable(true)) { + DEBUG_TRACE (DEBUG::LaunchControlXL, "dm_mb_flt_enabled() - filter exists\n"); + if (first_selected_stripable()->filter_enable_controllable(true)->get_value()) { + DEBUG_TRACE (DEBUG::LaunchControlXL, "dm_mb_flt_enabled: get_value true\n"); + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + DEBUG_TRACE (DEBUG::LaunchControlXL, string_compose("dm_mb_flt_enabled: dev_status: %1\n", (int)dev_status)); + return dev_status; +} + + +void +LaunchControlXL::dm_mb_flt_switch() +{ + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->filter_enable_controllable(true)) { + first_selected_stripable()->filter_enable_controllable(true)->set_value + (!first_selected_stripable()->filter_enable_controllable(true)->get_value(), PBD::Controllable::NoGroup ); + } +} + + + +void +LaunchControlXL::dm_mb_flt_frq (KnobID k, bool hpf) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + if (hpf) { + ac = first_selected_stripable()->filter_freq_controllable(true); + } else { + ac = first_selected_stripable()->filter_freq_controllable(false); + } + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +uint8_t +LaunchControlXL::dm_mb_check_send_knob (KnobID k) +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t send = static_cast (k) - 16 + 4 * send_bank_base(); + + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->send_enable_controllable(send)) { + dev_status = dev_inactive; + if (first_selected_stripable()->send_enable_controllable(send)->get_value()) { + dev_status = dev_active; + } + } + + return dev_status; +} + +uint8_t +LaunchControlXL::dm_mb_check_send_button (uint8_t s) +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + + uint8_t send = s + 4 * send_bank_base(); + + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->send_enable_controllable(send)) { + dev_status = dev_inactive; + if (first_selected_stripable()->send_enable_controllable(send)->get_value()) { + dev_status = dev_active; + } + } + + return dev_status; +} + + + +void +LaunchControlXL::dm_mb_sends (KnobID k) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + + uint8_t send = static_cast (k) - 16 + 4 * send_bank_base(); + DEBUG_TRACE (DEBUG::LaunchControlXL, string_compose("dm_mb_send: knobid '%1'\n", k)); + DEBUG_TRACE (DEBUG::LaunchControlXL, string_compose("dm_mb_send: send '%1'\n", (int)send)); + + + if (buttons_down.find(Device) != buttons_down.end()) { // Device button hold + ac = first_selected_stripable()->send_pan_azi_controllable(send); + } else { + ac = first_selected_stripable()->send_level_controllable(send); + } + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +uint8_t +LaunchControlXL::dm_mb_comp_enabled() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + if (first_selected_stripable()->comp_enable_controllable()) { + if (first_selected_stripable()->comp_enable_controllable()->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + + return dev_status; +} + +void +LaunchControlXL::dm_mb_comp_switch() +{ + DEBUG_TRACE (DEBUG::LaunchControlXL, "dm_mb_comp_siwtch() \n"); + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->comp_enable_controllable()) { + DEBUG_TRACE (DEBUG::LaunchControlXL, "comp_enable_controllable exists\n"); + DEBUG_TRACE (DEBUG::LaunchControlXL, string_compose("comp_enable_controllable(): '%1'\n", first_selected_stripable()->comp_enable_controllable()->get_value() )); + first_selected_stripable()->comp_enable_controllable()->set_value + (!first_selected_stripable()->comp_enable_controllable()->get_value(), PBD::Controllable::NoGroup); + } + +} + +void +LaunchControlXL::dm_mb_comp (KnobID k, CompParam c) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + + switch (c) { + case (CompMakeup): + ac = first_selected_stripable()->comp_makeup_controllable(); + break; + case (CompMode): + ac = first_selected_stripable()->comp_mode_controllable(); + break; + case (CompSpeed): + ac = first_selected_stripable()->comp_speed_controllable(); + break; + } + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +void +LaunchControlXL::dm_mb_comp_thresh (FaderID id) { + + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr fader; + + IDFaderMap::iterator f = id_fader_map.find(id); + + if (f != id_fader_map.end()) { + fader = f->second; + } + + ac = first_selected_stripable()->comp_threshold_controllable(); + if (ac && check_pick_up(fader, ac)) { + ac->set_value ( ac->interface_to_internal( fader->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +uint8_t +LaunchControlXL::dm_mb_has_tapedrive() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->mixbus() || first_selected_stripable()->is_master()) { + dev_status = dev_active; + } + + return dev_status; +} + +void +LaunchControlXL::dm_mb_tapedrive (KnobID k) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr ac; + boost::shared_ptr knob = knob_by_id (k); + + ac = first_selected_stripable()->tape_drive_controllable(); + + if (ac && check_pick_up(knob, ac)) { + ac->set_value ( ac->interface_to_internal( knob->value() / 127.0), PBD::Controllable::UseGroup ); + } +} + +uint8_t +LaunchControlXL::dm_mb_master_assign_enabled() +{ + if (!first_selected_stripable()) { + return dev_nonexistant; + } + + uint8_t dev_status = dev_nonexistant; + + if (first_selected_stripable()->master_send_enable_controllable()) { + if (first_selected_stripable()->master_send_enable_controllable()->get_value()) { + dev_status = dev_active; + } else { + dev_status = dev_inactive; + } + } + + return dev_status; +} + +void +LaunchControlXL::dm_mb_master_assign_switch() +{ + if (!first_selected_stripable()) { + return; + } + + if (first_selected_stripable()->master_send_enable_controllable()) { + first_selected_stripable()->master_send_enable_controllable()->set_value + (!first_selected_stripable()->master_send_enable_controllable()->get_value(), PBD::Controllable::NoGroup ); + } +} + +void +LaunchControlXL::dm_mb_send_switch(ButtonID id) +{ + if (!first_selected_stripable()) { + return; + } + + boost::shared_ptr