From 8f7fa7d93b47665c14e452b06e0fb017d0dd653d Mon Sep 17 00:00:00 2001 From: Paul Davis Date: Fri, 13 Apr 2012 16:11:55 +0000 Subject: MCP: timeout display of value when altering with fader or pot; range ops on strip buttons should work; select logic may be broken git-svn-id: svn://localhost/ardour2/branches/3.0@11959 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/ardour/ardour/panner.h | 3 - libs/panners/1in2out/panner_1in2out.cc | 6 +- libs/panners/2in2out/panner_2in2out.cc | 8 +- libs/surfaces/control_protocol/control_protocol.cc | 6 +- .../control_protocol/control_protocol.h | 7 +- libs/surfaces/generic_midi/midifunction.cc | 3 +- libs/surfaces/mackie/device_info.cc | 1 - libs/surfaces/mackie/mackie_control_protocol.cc | 157 +++++++++------------ libs/surfaces/mackie/mackie_control_protocol.h | 37 ++--- libs/surfaces/mackie/strip.cc | 109 +++++++++++--- libs/surfaces/mackie/strip.h | 7 +- libs/surfaces/mackie/surface.cc | 4 +- libs/surfaces/mackie/surface.h | 2 +- 13 files changed, 199 insertions(+), 151 deletions(-) (limited to 'libs') diff --git a/libs/ardour/ardour/panner.h b/libs/ardour/ardour/panner.h index 6f54ea7d79..51d75ebf03 100644 --- a/libs/ardour/ardour/panner.h +++ b/libs/ardour/ardour/panner.h @@ -142,9 +142,6 @@ public: boost::shared_ptr pannable() const { return _pannable; } - //virtual std::string describe_parameter (Evoral::Parameter); - //virtual std::string value_as_string (Evoral::Parameter, double val); - static bool equivalent (pan_t a, pan_t b) { return fabsf (a - b) < 0.002; // about 1 degree of arc for a stereo panner } diff --git a/libs/panners/1in2out/panner_1in2out.cc b/libs/panners/1in2out/panner_1in2out.cc index 2fb2df7e9a..d84af57ade 100644 --- a/libs/panners/1in2out/panner_1in2out.cc +++ b/libs/panners/1in2out/panner_1in2out.cc @@ -364,9 +364,13 @@ Panner1in2out::value_as_string (boost::shared_ptr ac) const This is pretty wierd, but its the way audio engineers expect it. Just remember that the center of the USA isn't Kansas, its (50LA, 50NY) and it will all make sense. + + This is designed to be as narrow as possible. Dedicated + panner GUIs can do their own version of this if they need + something less compact. */ - return string_compose (_("L:%1 R:%2"), (int) rint (100.0 * (1.0 - val)), + return string_compose (_("L%1R%2"), (int) rint (100.0 * (1.0 - val)), (int) rint (100.0 * val)); default: diff --git a/libs/panners/2in2out/panner_2in2out.cc b/libs/panners/2in2out/panner_2in2out.cc index c9dac08cf1..8e798315d0 100644 --- a/libs/panners/2in2out/panner_2in2out.cc +++ b/libs/panners/2in2out/panner_2in2out.cc @@ -478,11 +478,15 @@ Panner2in2out::value_as_string (boost::shared_ptr ac) const This is pretty wierd, but its the way audio engineers expect it. Just remember that the center of the USA isn't Kansas, its (50LA, 50NY) and it will all make sense. + + This is designed to be as narrow as possible. Dedicated + panner GUIs can do their own version of this if they need + something less compact. */ - return string_compose (_("L:%1 R:%2"), (int) rint (100.0 * (1.0 - val)), + return string_compose (_("L%1R%2"), (int) rint (100.0 * (1.0 - val)), (int) rint (100.0 * val)); - + case PanWidthAutomation: return string_compose (_("Width: %1%%"), (int) floor (100.0 * val)); diff --git a/libs/surfaces/control_protocol/control_protocol.cc b/libs/surfaces/control_protocol/control_protocol.cc index cf6a7c1800..e2bc1673d8 100644 --- a/libs/surfaces/control_protocol/control_protocol.cc +++ b/libs/surfaces/control_protocol/control_protocol.cc @@ -38,8 +38,6 @@ Signal0 ControlProtocol::Enter; Signal0 ControlProtocol::Undo; Signal0 ControlProtocol::Redo; Signal1 ControlProtocol::ScrollTimeline; -Signal1 ControlProtocol::SelectByRID; -Signal0 ControlProtocol::UnselectTrack; Signal1 ControlProtocol::GotoView; Signal0 ControlProtocol::CloseDialog; PBD::Signal0 ControlProtocol::VerticalZoomInAll; @@ -47,6 +45,10 @@ PBD::Signal0 ControlProtocol::VerticalZoomOutAll; PBD::Signal0 ControlProtocol::VerticalZoomInSelected; PBD::Signal0 ControlProtocol::VerticalZoomOutSelected; PBD::Signal1 ControlProtocol::TrackSelectionChanged; +PBD::Signal1 ControlProtocol::AddRouteToSelection; +PBD::Signal1 ControlProtocol::SetRouteSelection; +PBD::Signal1 ControlProtocol::RemoveRouteFromSelection; +PBD::Signal0 ControlProtocol::ClearRouteSelection; ControlProtocol::ControlProtocol (Session& s, string str, EventLoop* evloop) : BasicUI (s), diff --git a/libs/surfaces/control_protocol/control_protocol/control_protocol.h b/libs/surfaces/control_protocol/control_protocol/control_protocol.h index 68a1461c10..89e9e6c4d5 100644 --- a/libs/surfaces/control_protocol/control_protocol/control_protocol.h +++ b/libs/surfaces/control_protocol/control_protocol/control_protocol.h @@ -67,8 +67,6 @@ class ControlProtocol : virtual public sigc::trackable, public PBD::Stateful, pu static PBD::Signal0 Undo; static PBD::Signal0 Redo; static PBD::Signal1 ScrollTimeline; - static PBD::Signal1 SelectByRID; - static PBD::Signal0 UnselectTrack; static PBD::Signal1 GotoView; static PBD::Signal0 CloseDialog; static PBD::Signal0 VerticalZoomInAll; @@ -76,6 +74,11 @@ class ControlProtocol : virtual public sigc::trackable, public PBD::Stateful, pu static PBD::Signal0 VerticalZoomInSelected; static PBD::Signal0 VerticalZoomOutSelected; + static PBD::Signal1 AddRouteToSelection; + static PBD::Signal1 SetRouteSelection; + static PBD::Signal1 RemoveRouteFromSelection; + static PBD::Signal0 ClearRouteSelection; + /* signals that one UI (e.g. the GUI) can emit to get all other UI's to respond. Typically this will always be GUI->"others" - the GUI pays no attention to these signals. diff --git a/libs/surfaces/generic_midi/midifunction.cc b/libs/surfaces/generic_midi/midifunction.cc index 926ee95a89..302ed0b552 100644 --- a/libs/surfaces/generic_midi/midifunction.cc +++ b/libs/surfaces/generic_midi/midifunction.cc @@ -131,8 +131,9 @@ MIDIFunction::execute () if (!_argument.empty()) { uint32_t rid; sscanf (_argument.c_str(), "%d", &rid); - _ui->SelectByRID (rid); + _ui->SetRouteSelection (rid); } + break; case TrackSetMute: break; case TrackSetSolo: diff --git a/libs/surfaces/mackie/device_info.cc b/libs/surfaces/mackie/device_info.cc index d2eaf9f279..9b15baf208 100644 --- a/libs/surfaces/mackie/device_info.cc +++ b/libs/surfaces/mackie/device_info.cc @@ -281,7 +281,6 @@ DeviceInfo::reload_device_info () if (di.set_state (*root, 3000) == 0) { /* version is ignored for now */ device_info[di.name()] = di; - std::cerr << di << '\n'; } } diff --git a/libs/surfaces/mackie/mackie_control_protocol.cc b/libs/surfaces/mackie/mackie_control_protocol.cc index ac5dc59044..3a39cc3522 100644 --- a/libs/surfaces/mackie/mackie_control_protocol.cc +++ b/libs/surfaces/mackie/mackie_control_protocol.cc @@ -389,8 +389,14 @@ MackieControlProtocol::periodic () return false; } + struct timeval now; + uint64_t now_usecs; + gettimeofday (&now, 0); + + now_usecs = (now.tv_sec * 1000000) + now.tv_usec; + for (Surfaces::iterator s = surfaces.begin(); s != surfaces.end(); ++s) { - (*s)->periodic (); + (*s)->periodic (now_usecs); } return true; @@ -1060,22 +1066,6 @@ MackieControlProtocol::handle_button_event (Surface& surface, Button& button, Bu } } -void -MackieControlProtocol::select_track (boost::shared_ptr r) -{ - if (_modifier_state == MODIFIER_SHIFT) { - r->gain_control()->set_value (0.0); - } else { - if (_current_selected_track > 0 && r->remote_control_id() == (uint32_t) _current_selected_track) { - UnselectTrack (); /* EMIT SIGNAL */ - _current_selected_track = -1; - } else { - SelectByRID (r->remote_control_id()); /* EMIT SIGNAL */ - _current_selected_track = r->remote_control_id();; - } - } -} - bool MackieControlProtocol::midi_input_handler (IOCondition ioc, MIDI::Port* port) { @@ -1210,112 +1200,91 @@ MackieControlProtocol::remove_down_select_button (int surface, int strip) } } -bool +void MackieControlProtocol::select_range () { - vector > routes; + RouteList routes; + pull_route_range (_down_select_buttons, routes); - if (routes.empty()) { - return false; + if (!routes.empty()) { + for (RouteList::iterator r = routes.begin(); r != routes.end(); ++r) { + if (r == routes.begin()) { + SetRouteSelection ((*r)->remote_control_id()); + } else { + AddRouteToSelection ((*r)->remote_control_id()); + } + } } - - /* do something */ - - return true; } void -MackieControlProtocol::add_down_solo_button (int surface, int strip) +MackieControlProtocol::add_down_button (AutomationType a, int surface, int strip) { - _down_solo_buttons.push_back ((surface<<8)|(strip&0xf)); -} + DownButtonMap::iterator m = _down_buttons.find (a); -void -MackieControlProtocol::remove_down_solo_button (int surface, int strip) -{ - list::iterator x = find (_down_solo_buttons.begin(), _down_solo_buttons.end(), (surface<<8)|(strip&0xf)); - if (x != _down_solo_buttons.end()) { - _down_solo_buttons.erase (x); + if (m == _down_buttons.end()) { + _down_buttons[a] = DownButtonList(); } -} -bool -MackieControlProtocol::solo_range () -{ - vector > routes; - pull_route_range (_down_solo_buttons, routes); - - if (routes.empty()) { - return false; - } - - /* do something */ - - return true; + _down_buttons[a].push_back ((surface<<8)|(strip&0xf)); } void -MackieControlProtocol::add_down_mute_button (int surface, int strip) +MackieControlProtocol::remove_down_button (AutomationType a, int surface, int strip) { - _down_mute_buttons.push_back ((surface<<8)|(strip&0xf)); -} + DownButtonMap::iterator m = _down_buttons.find (a); -void -MackieControlProtocol::remove_down_mute_button (int surface, int strip) -{ - list::iterator x = find (_down_mute_buttons.begin(), _down_mute_buttons.end(), (surface<<8)|(strip&0xf)); - if (x != _down_mute_buttons.end()) { - _down_mute_buttons.erase (x); + if (m == _down_buttons.end()) { + return; } -} -bool -MackieControlProtocol::mute_range () -{ - vector > routes; - pull_route_range (_down_mute_buttons, routes); + DownButtonList& l (m->second); + list::iterator x = find (l.begin(), l.end(), (surface<<8)|(strip&0xf)); - if (routes.empty()) { - return false; + if (x != l.end()) { + l.erase (x); } - - /* do something */ - - return true; } -void -MackieControlProtocol::add_down_recenable_button (int surface, int strip) -{ - _down_recenable_buttons.push_back ((surface<<8)|(strip&0xf)); -} - -void -MackieControlProtocol::remove_down_recenable_button (int surface, int strip) +MackieControlProtocol::ControlList +MackieControlProtocol::down_controls (AutomationType p) { - list::iterator x = find (_down_recenable_buttons.begin(), _down_recenable_buttons.end(), (surface<<8)|(strip&0xf)); - if (x != _down_recenable_buttons.end()) { - _down_recenable_buttons.erase (x); - } -} + ControlList controls; + RouteList routes; -bool -MackieControlProtocol::recenable_range () -{ - vector > routes; - pull_route_range (_down_recenable_buttons, routes); + DownButtonMap::iterator m = _down_buttons.find (p); - if (routes.empty()) { - return false; + if (m == _down_buttons.end()) { + return controls; + } + + pull_route_range (m->second, routes); + + switch (p) { + case GainAutomation: + for (RouteList::iterator r = routes.begin(); r != routes.end(); ++r) { + controls.push_back ((*r)->gain_control()); + } + break; + case SoloAutomation: + for (RouteList::iterator r = routes.begin(); r != routes.end(); ++r) { + controls.push_back ((*r)->solo_control()); + } + break; + case MuteAutomation: + for (RouteList::iterator r = routes.begin(); r != routes.end(); ++r) { + controls.push_back ((*r)->mute_control()); + } + break; + default: + break; } - /* do something */ + return controls; - return true; } - - + struct ButtonRangeSorter { bool operator() (const uint32_t& a, const uint32_t& b) { return (a>>8) < (b>>8) // a.surface < b.surface @@ -1325,7 +1294,7 @@ struct ButtonRangeSorter { }; void -MackieControlProtocol::pull_route_range (list& down, vector >& selected) +MackieControlProtocol::pull_route_range (list& down, RouteList& selected) { ButtonRangeSorter cmp; diff --git a/libs/surfaces/mackie/mackie_control_protocol.h b/libs/surfaces/mackie/mackie_control_protocol.h index ed2472f2fd..18919954c4 100644 --- a/libs/surfaces/mackie/mackie_control_protocol.h +++ b/libs/surfaces/mackie/mackie_control_protocol.h @@ -30,9 +30,7 @@ #include #include "pbd/abstract_ui.h" - #include "midi++/types.h" - #include "ardour/types.h" #include "control_protocol/control_protocol.h" @@ -148,8 +146,6 @@ class MackieControlProtocol void* get_gui () const; void tear_down_gui (); - void select_track (boost::shared_ptr r); - void handle_button_event (Mackie::Surface&, Mackie::Button& button, Mackie::ButtonState); void notify_route_added (ARDOUR::RouteList &); @@ -184,21 +180,15 @@ class MackieControlProtocol int modifier_state() const { return _modifier_state; } + typedef std::list > ControlList; + + void add_down_button (ARDOUR::AutomationType, int surface, int strip); + void remove_down_button (ARDOUR::AutomationType, int surface, int strip); + ControlList down_controls (ARDOUR::AutomationType); + void add_down_select_button (int surface, int strip); void remove_down_select_button (int surface, int strip); - bool select_range (); - - void add_down_solo_button (int surface, int strip); - void remove_down_solo_button (int surface, int strip); - bool solo_range (); - - void add_down_mute_button (int surface, int strip); - void remove_down_mute_button (int surface, int strip); - bool mute_range (); - - void add_down_recenable_button (int surface, int strip); - void remove_down_recenable_button (int surface, int strip); - bool recenable_range (); + void select_range (); protected: // shut down the surface @@ -302,14 +292,15 @@ class MackieControlProtocol void gui_track_selection_changed (ARDOUR::RouteNotificationListPtr); + /* BUTTON HANDLING */ - - std::list _down_select_buttons; - std::list _down_solo_buttons; - std::list _down_mute_buttons; - std::list _down_recenable_buttons; - void pull_route_range (std::list& down, std::vector >& selected); + typedef std::list DownButtonList; + typedef std::map DownButtonMap; + DownButtonMap _down_buttons; + DownButtonList _down_select_buttons; + + void pull_route_range (DownButtonList&, ARDOUR::RouteList&); /* implemented button handlers */ Mackie::LedState frm_left_press(Mackie::Button &); diff --git a/libs/surfaces/mackie/strip.cc b/libs/surfaces/mackie/strip.cc index aedd8548ec..eaeb94e72c 100644 --- a/libs/surfaces/mackie/strip.cc +++ b/libs/surfaces/mackie/strip.cc @@ -21,6 +21,8 @@ #include #include "strip.h" +#include + #include "midi++/port.h" #include "pbd/compose.h" @@ -70,6 +72,7 @@ Strip::Strip (Surface& s, const std::string& name, int index, StripControlDefini , _index (index) , _surface (&s) , _controls_locked (false) + , _reset_display_at (0) , _last_gain_position_written (-1.0) , _last_pan_position_written (-1.0) { @@ -301,7 +304,8 @@ Strip::notify_gain_changed (bool force_update) snprintf (buf, sizeof (buf), "%6.1f", dB); _surface->write (display (1, buf)); } - + + queue_display_reset (500); _last_gain_position_written = pos; } else { @@ -363,11 +367,21 @@ Strip::notify_panner_changed (bool force_update) double pos = pannable->pan_azimuth_control->internal_to_interface (pannable->pan_azimuth_control->get_value()); if (force_update || pos != _last_pan_position_written) { + if (_surface->mcp().flip_mode()) { + _surface->write (_fader->set_position (pos)); + } else { _surface->write (_vpot->set_all (pos, true, Pot::dot)); } + + if (pannable->panner()) { + string str = pannable->panner()->value_as_string (pannable->pan_azimuth_control); + _surface->write (display (1, str)); + queue_display_reset (500); + } + _last_pan_position_written = pos; } } @@ -377,7 +391,11 @@ Strip::notify_panner_changed (bool force_update) void Strip::handle_button (Button& button, ButtonState bs) { - button.set_in_use (bs == press); + if (bs == press) { + button.set_in_use (true); + } else { + button.set_in_use (false); + } DEBUG_TRACE (DEBUG::MackieControl, string_compose ("strip %1 handling button %2\n", _index, button.id())); @@ -397,9 +415,11 @@ Strip::handle_button (Button& button, ButtonState bs) return; } - if (_route) { - _surface->mcp().select_track (_route); - } + _surface->mcp().add_down_select_button (_surface->number(), _index); + _surface->mcp().select_range (); + + } else { + _surface->mcp().remove_down_select_button (_surface->number(), _index); } return; @@ -415,10 +435,6 @@ Strip::handle_button (Button& button, ButtonState bs) _fader->set_in_use (state); _fader->start_touch (_surface->mcp().transport_frame(), modified); - if (!_surface->mcp().device_info().has_touch_sense_faders()) { - _surface->mcp().add_in_use_timeout (*_surface, *_fader, _fader->control (modified)); - } - if (bs != press) { /* fader touch ended, revert back to label display for fader */ _surface->write (display (1, static_display_string())); @@ -430,14 +446,37 @@ Strip::handle_button (Button& button, ButtonState bs) boost::shared_ptr control = button.control (modified); if (control) { - if (ms & MackieControlProtocol::MODIFIER_OPTION) { - /* reset to default/normal value */ - DEBUG_TRACE (DEBUG::MackieControl, string_compose ("reset %1 to default of %2\n", control->name(), control->normal())); - control->set_value (control->normal()); + + if (bs == press) { + _surface->mcp().add_down_button ((AutomationType) control->parameter().type(), _surface->number(), _index); + + float new_value; + + if (ms & MackieControlProtocol::MODIFIER_OPTION) { + /* reset to default/normal value */ + new_value = control->normal(); + } else { + new_value = control->get_value() ? 0.0 : 1.0; + } + + /* get all controls that either have their + * button down or are within a range of + * several down buttons + */ + + MackieControlProtocol::ControlList controls = _surface->mcp().down_controls ((AutomationType) control->parameter().type()); + + + /* apply change */ + + for (MackieControlProtocol::ControlList::iterator c = controls.begin(); c != controls.end(); ++c) { + (*c)->set_value (new_value); + } + } else { - DEBUG_TRACE (DEBUG::MackieControl, string_compose ("toggle %1 to default of %2\n", control->name(), control->get_value() ? 0.0 : 1.0)); - control->set_value (control->get_value() ? 0.0 : 1.0); + _surface->mcp().remove_down_button ((AutomationType) control->parameter().type(), _surface->number(), _index); } + } else { DEBUG_TRACE (DEBUG::MackieControl, string_compose ("button has no control at present (modified ? %1)\n", modified)); } @@ -483,7 +522,7 @@ Strip::handle_pot (Pot& pot, float delta) } void -Strip::periodic () +Strip::periodic (uint64_t usecs) { if (!_route) { return; @@ -491,6 +530,10 @@ Strip::periodic () update_automation (); update_meter (); + + if (_reset_display_at && _reset_display_at < usecs) { + reset_display (); + } } void @@ -605,9 +648,9 @@ string Strip::static_display_string () const { if (_surface->mcp().flip_mode()) { - return "Pan"; - } else { return "Fader"; + } else { + return "Pan"; } } @@ -647,3 +690,33 @@ Strip::flip_mode_changed (bool notify) notify_all (); } } + +void +Strip::queue_display_reset (uint32_t msecs) +{ + struct timeval now; + struct timeval delta; + struct timeval when; + gettimeofday (&now, 0); + + delta.tv_sec = msecs/1000; + delta.tv_usec = (msecs - ((msecs/1000) * 1000)) * 1000; + + timeradd (&now, &delta, &when); + + _reset_display_at = (when.tv_sec * 1000000) + when.tv_usec; +} + +void +Strip::clear_display_reset () +{ + _reset_display_at = 0; +} + +void +Strip::reset_display () +{ + _surface->write (display (1, static_display_string())); + clear_display_reset (); +} + diff --git a/libs/surfaces/mackie/strip.h b/libs/surfaces/mackie/strip.h index ca9862c6e3..ec211eb5fe 100644 --- a/libs/surfaces/mackie/strip.h +++ b/libs/surfaces/mackie/strip.h @@ -63,7 +63,7 @@ public: void handle_fader (Fader&, float position); void handle_pot (Pot&, float delta); - void periodic (); + void periodic (uint64_t now_usecs); MidiByteArray display (uint32_t line_number, const std::string&); MidiByteArray blank_display (uint32_t line_number); @@ -89,6 +89,7 @@ private: int _index; Surface* _surface; bool _controls_locked; + uint64_t _reset_display_at; boost::shared_ptr _route; PBD::ScopedConnectionList route_connections; @@ -109,6 +110,10 @@ private: void update_meter (); std::string static_display_string () const; + + void queue_display_reset (uint32_t msecs); + void clear_display_reset (); + void reset_display (); }; } diff --git a/libs/surfaces/mackie/surface.cc b/libs/surfaces/mackie/surface.cc index 894baeac5e..4374ae2d30 100644 --- a/libs/surfaces/mackie/surface.cc +++ b/libs/surfaces/mackie/surface.cc @@ -618,10 +618,10 @@ Surface::zero_all () } void -Surface::periodic () +Surface::periodic (uint64_t now_usecs) { for (Strips::iterator s = strips.begin(); s != strips.end(); ++s) { - (*s)->periodic (); + (*s)->periodic (now_usecs); } } diff --git a/libs/surfaces/mackie/surface.h b/libs/surfaces/mackie/surface.h index 8dd8792231..6bdb575847 100644 --- a/libs/surfaces/mackie/surface.h +++ b/libs/surfaces/mackie/surface.h @@ -81,7 +81,7 @@ public: const MidiByteArray& sysex_hdr() const; - void periodic (); + void periodic (uint64_t now_usecs); void handle_midi_pitchbend_message (MIDI::Parser&, MIDI::pitchbend_t, uint32_t channel_id); void handle_midi_controller_message (MIDI::Parser&, MIDI::EventTwoBytes*); -- cgit v1.2.3