From 2bae75fa0b3d10b844738e0cb5d03c5de23d0c49 Mon Sep 17 00:00:00 2001 From: Paul Davis Date: Wed, 25 Apr 2012 21:21:36 +0000 Subject: MCP: dynamic ipMIDI ports, more default key bindings, various minor fixes git-svn-id: svn://localhost/ardour2/branches/3.0@12092 d708f5d6-7413-0410-9779-e7cbd77b26cf --- libs/ardour/ardour/rc_configuration_vars.h | 2 - libs/ardour/control_protocol_manager.cc | 12 +- libs/ardour/midi_ui.cc | 2 - libs/surfaces/mackie/button.cc | 4 +- libs/surfaces/mackie/device_info.cc | 4 + libs/surfaces/mackie/device_profile.cc | 5 +- libs/surfaces/mackie/gui.cc | 20 +++- libs/surfaces/mackie/gui.h | 1 + libs/surfaces/mackie/interface.cc | 2 +- libs/surfaces/mackie/mackie_control_protocol.cc | 142 ++++++++++++++++-------- libs/surfaces/mackie/mackie_control_protocol.h | 10 +- libs/surfaces/mackie/surface_port.cc | 2 +- 12 files changed, 135 insertions(+), 71 deletions(-) (limited to 'libs') diff --git a/libs/ardour/ardour/rc_configuration_vars.h b/libs/ardour/ardour/rc_configuration_vars.h index cd093d1d80..1f9e3c1037 100644 --- a/libs/ardour/ardour/rc_configuration_vars.h +++ b/libs/ardour/ardour/rc_configuration_vars.h @@ -50,8 +50,6 @@ CONFIG_VARIABLE (bool, first_midi_bank_is_zero, "diplay-first-midi-bank-as-zero" CONFIG_VARIABLE (uint32_t, feedback_interval_ms, "feedback-interval-ms", 100) CONFIG_VARIABLE (bool, use_tranzport, "use-tranzport", false) -CONFIG_VARIABLE (std::string, mackie_device_name, "mackie-device-name", "Mackie Control Universal Pro") -CONFIG_VARIABLE (std::string, mackie_device_profile, "mackie-device-profile", "default") CONFIG_VARIABLE (RemoteModel, remote_model, "remote-model", MixerOrdered) /* disk operations */ diff --git a/libs/ardour/control_protocol_manager.cc b/libs/ardour/control_protocol_manager.cc index 876091fa7d..c72d3f31d0 100644 --- a/libs/ardour/control_protocol_manager.cc +++ b/libs/ardour/control_protocol_manager.cc @@ -75,8 +75,16 @@ ControlProtocolManager::set_session (Session* s) instantiate (**i); (*i)->requested = false; - if ((*i)->protocol && (*i)->state) { - (*i)->protocol->set_state (*(*i)->state, Stateful::loading_state_version); + if ((*i)->protocol) { + if ((*i)->state) { + (*i)->protocol->set_state (*(*i)->state, Stateful::loading_state_version); + } else { + /* guarantee a call to + set_state() whether we have + existing state or not + */ + (*i)->protocol->set_state (XMLNode(""), Stateful::loading_state_version); + } } } } diff --git a/libs/ardour/midi_ui.cc b/libs/ardour/midi_ui.cc index e9e9eafb99..770a371457 100644 --- a/libs/ardour/midi_ui.cc +++ b/libs/ardour/midi_ui.cc @@ -134,8 +134,6 @@ MidiControlUI::reset_ports () for (MIDI::Manager::PortList::const_iterator i = plist->begin(); i != plist->end(); ++i) { - cerr << "MIDI UI looking at port " << (*i)->name() << endl; - if (!(*i)->centrally_parsed()) { continue; } diff --git a/libs/surfaces/mackie/button.cc b/libs/surfaces/mackie/button.cc index 11fc391930..dc26429a63 100644 --- a/libs/surfaces/mackie/button.cc +++ b/libs/surfaces/mackie/button.cc @@ -51,8 +51,8 @@ Button::name_to_id (const std::string& name) if (!g_strcasecmp (name.c_str(), "ChannelRight")) { return ChannelRight; } if (!g_strcasecmp (name.c_str(), "Flip")) { return Flip; } if (!g_strcasecmp (name.c_str(), "Edit")) { return Edit; } - if (!g_strcasecmp (name.c_str(), "NameValue")) { return NameValue; } - if (!g_strcasecmp (name.c_str(), "TimecodeBeats")) { return TimecodeBeats; } + if (!g_strcasecmp (name.c_str(), "Name/Value")) { return NameValue; } + if (!g_strcasecmp (name.c_str(), "Timecode/Beats")) { return TimecodeBeats; } if (!g_strcasecmp (name.c_str(), "F1")) { return F1; } if (!g_strcasecmp (name.c_str(), "F2")) { return F2; } if (!g_strcasecmp (name.c_str(), "F3")) { return F3; } diff --git a/libs/surfaces/mackie/device_info.cc b/libs/surfaces/mackie/device_info.cc index ba14d9f8fd..e9e5d1b04b 100644 --- a/libs/surfaces/mackie/device_info.cc +++ b/libs/surfaces/mackie/device_info.cc @@ -209,12 +209,16 @@ DeviceInfo::set_state (const XMLNode& node, int /* version */) } } + /* strip count is mandatory */ + if ((child = node.child ("Strips")) != 0) { if ((prop = child->property ("value")) != 0) { if ((_strip_cnt = atoi (prop->value())) == 0) { _strip_cnt = 8; } } + } else { + return -1; } if ((child = node.child ("Extenders")) != 0) { diff --git a/libs/surfaces/mackie/device_profile.cc b/libs/surfaces/mackie/device_profile.cc index 462c43b678..04975270ab 100644 --- a/libs/surfaces/mackie/device_profile.cc +++ b/libs/surfaces/mackie/device_profile.cc @@ -107,13 +107,11 @@ DeviceProfile::reload_device_profiles () if (!devprofiles) { error << "No MCP device info files found using " << spath.to_string() << endmsg; - std::cerr << "No MCP device info files found using " << spath.to_string() << std::endl; return; } if (devprofiles->empty()) { error << "No MCP device info files found using " << spath.to_string() << endmsg; - std::cerr << "No MCP device info files found using " << spath.to_string() << std::endl; return; } @@ -288,7 +286,7 @@ DeviceProfile::set_button_action (Button::ID id, int modifier_state, const strin ButtonActionMap::iterator i = _button_map.find (id); if (i == _button_map.end()) { - return; + i = _button_map.insert (std::make_pair (id, ButtonActions())).first; } string action (act); @@ -360,6 +358,7 @@ DeviceProfile::save () XMLTree tree; tree.set_root (&get_state()); + if (!tree.write (fullpath.to_string())) { error << string_compose ("MCP profile not saved to %1", fullpath.to_string()) << endmsg; } diff --git a/libs/surfaces/mackie/gui.cc b/libs/surfaces/mackie/gui.cc index 1ecadec540..adaf2df945 100644 --- a/libs/surfaces/mackie/gui.cc +++ b/libs/surfaces/mackie/gui.cc @@ -72,7 +72,7 @@ MackieControlProtocolGUI::MackieControlProtocolGUI (MackieControlProtocol& p) , touch_sensitivity_adjustment (0, 0, 9, 1, 4) , touch_sensitivity_scale (touch_sensitivity_adjustment) , recalibrate_fader_button (_("Recalibrate Faders")) - , ipmidi_base_port_adjustment (21928, 0, 32767, 1, 1000) + , ipmidi_base_port_adjustment (_cp.ipmidi_base(), 0, 32767, 1, 1000) , ipmidi_base_port_spinner (ipmidi_base_port_adjustment) { Gtk::Label* l; @@ -141,6 +141,7 @@ MackieControlProtocolGUI::MackieControlProtocolGUI (MackieControlProtocol& p) table->attach (ipmidi_base_port_spinner, 1, 2, 7, 8, AttachOptions(FILL|EXPAND), AttachOptions (0)); ipmidi_base_port_spinner.set_sensitive (_cp.device_info().uses_ipmidi()); + ipmidi_base_port_adjustment.signal_value_changed().connect (sigc::mem_fun (*this, &MackieControlProtocolGUI::ipmidi_spinner_changed)); vector profiles; @@ -344,7 +345,7 @@ MackieControlProtocolGUI::refresh_function_key_editor () Glib::RefPtr act; string action; - const string defstring = "def"; + const string defstring = "\u2022"; action = dp.get_button_action (bid, 0); if (action.empty()) { @@ -432,12 +433,12 @@ MackieControlProtocolGUI::action_changed (const Glib::ustring &sPath, const Glib std::map::iterator i = action_map.find (text); - cerr << "Changed to " << text << endl; - if (i == action_map.end()) { return; } + cerr << "Changed to " << i->first << " aka " << i->second << endl; + Glib::RefPtr act = ActionManager::get_action (i->second.c_str()); if (act) { @@ -474,8 +475,9 @@ MackieControlProtocolGUI::action_changed (const Glib::ustring &sPath, const Glib } _cp.device_profile().set_button_action ((*row)[function_key_columns.id], modifier, i->second); + } else { + std::cerr << "no such action\n"; } - } } @@ -497,7 +499,13 @@ MackieControlProtocolGUI::profile_combo_changed () string profile = _profile_combo.get_active_text(); _cp.set_profile (profile); - ARDOUR::Config->set_mackie_device_profile (profile); refresh_function_key_editor (); } + +void +MackieControlProtocolGUI::ipmidi_spinner_changed () +{ + cerr << "Set IP MIDI base to " << ipmidi_base_port_spinner.get_value() << endl; + _cp.set_ipmidi_base ((int16_t) lrintf (ipmidi_base_port_spinner.get_value())); +} diff --git a/libs/surfaces/mackie/gui.h b/libs/surfaces/mackie/gui.h index f8268b9e35..9af0c21cab 100644 --- a/libs/surfaces/mackie/gui.h +++ b/libs/surfaces/mackie/gui.h @@ -92,6 +92,7 @@ class MackieControlProtocolGUI : public Gtk::Notebook void surface_combo_changed (); void profile_combo_changed (); + void ipmidi_spinner_changed (); std::map action_map; // map from action names to paths diff --git a/libs/surfaces/mackie/interface.cc b/libs/surfaces/mackie/interface.cc index a32ad42bb7..294a222a6b 100644 --- a/libs/surfaces/mackie/interface.cc +++ b/libs/surfaces/mackie/interface.cc @@ -36,7 +36,7 @@ new_mackie_protocol (ControlProtocolDescriptor*, Session* s) try { mcp = new MackieControlProtocol (*s); - mcp->set_active (true); + /* do not set active here - wait for set_state() */ } catch (exception & e) { error << "Error instantiating MackieControlProtocol: " << e.what() << endmsg; diff --git a/libs/surfaces/mackie/mackie_control_protocol.cc b/libs/surfaces/mackie/mackie_control_protocol.cc index f93379f3e7..93202f607b 100644 --- a/libs/surfaces/mackie/mackie_control_protocol.cc +++ b/libs/surfaces/mackie/mackie_control_protocol.cc @@ -35,6 +35,7 @@ #include "midi++/types.h" #include "midi++/port.h" +#include "midi++/ipmidi_port.h" #include "pbd/pthread_utils.h" #include "pbd/error.h" #include "pbd/memento_command.h" @@ -104,15 +105,14 @@ MackieControlProtocol::MackieControlProtocol (Session& session) , _view_mode (Mixer) , _current_selected_track (-1) , _modifier_state (0) + , _ipmidi_base (MIDI::IPMIDIPort::lowest_ipmidi_port_default) + , needs_ipmidi_restart (false) { DEBUG_TRACE (DEBUG::MackieControl, "MackieControlProtocol::MackieControlProtocol\n"); DeviceInfo::reload_device_info (); DeviceProfile::reload_device_profiles (); - set_device (Config->get_mackie_device_name()); - set_profile (Config->get_mackie_device_profile()); - TrackSelectionChanged.connect (gui_connections, MISSING_INVALIDATOR, boost::bind (&MackieControlProtocol::gui_track_selection_changed, this, _1), this); _instance = this; @@ -353,37 +353,30 @@ MackieControlProtocol::set_active (bool yn) return 0; } - try - { - if (yn) { - - /* start event loop */ - - BaseUI::run (); - - create_surfaces (); - connect_session_signals (); - _active = true; - update_surfaces (); - - /* set up periodic task for metering and automation - */ - - Glib::RefPtr periodic_timeout = Glib::TimeoutSource::create (100); // milliseconds - periodic_connection = periodic_timeout->connect (sigc::mem_fun (*this, &MackieControlProtocol::periodic)); - periodic_timeout->attach (main_loop()->get_context()); + if (yn) { + + /* start event loop */ + + BaseUI::run (); + + create_surfaces (); + connect_session_signals (); + _active = true; + update_surfaces (); + + /* set up periodic task for metering and automation + */ + + Glib::RefPtr periodic_timeout = Glib::TimeoutSource::create (100); // milliseconds + periodic_connection = periodic_timeout->connect (sigc::mem_fun (*this, &MackieControlProtocol::periodic)); + periodic_timeout->attach (main_loop()->get_context()); + + } else { - } else { - BaseUI::quit (); - close(); - _active = false; - } - } - - catch (exception & e) { - DEBUG_TRACE (DEBUG::MackieControl, string_compose ("set_active to false because exception caught: %1\n", e.what())); + BaseUI::quit (); + close (); _active = false; - throw; + } return 0; @@ -396,6 +389,11 @@ MackieControlProtocol::periodic () return false; } + if (needs_ipmidi_restart) { + ipmidi_restart (); + return true; + } + struct timeval now; uint64_t now_usecs; gettimeofday (&now, 0); @@ -475,8 +473,6 @@ MackieControlProtocol::update_surfaces() return; } - - // do the initial bank switch to connect signals // _current_initial_bank is initialised by set_state switch_banks (_current_initial_bank, true); @@ -549,10 +545,6 @@ MackieControlProtocol::set_device (const string& device_name) _device_info = d->second; - /* store it away in a global location */ - - Config->set_mackie_device_name (device_name); - if (_active) { create_surfaces (); switch_banks (0, true); @@ -637,15 +629,22 @@ XMLNode& MackieControlProtocol::get_state() { DEBUG_TRACE (DEBUG::MackieControl, "MackieControlProtocol::get_state\n"); + char buf[16]; // add name of protocol XMLNode* node = new XMLNode (X_("Protocol")); node->add_property (X_("name"), ARDOUR::ControlProtocol::_name); // add current bank - ostringstream os; - os << _current_initial_bank; - node->add_property (X_("bank"), os.str()); + snprintf (buf, sizeof (buf), "%d", _current_initial_bank); + node->add_property (X_("bank"), buf); + + // ipMIDI base port (possibly not used) + snprintf (buf, sizeof (buf), "%d", _ipmidi_base); + node->add_property (X_("ipmidi-base"), buf); + + node->add_property (X_("device-profile"), _device_profile.name()); + node->add_property (X_("device-name"), _device_info.name()); return *node; } @@ -657,15 +656,34 @@ MackieControlProtocol::set_state (const XMLNode & node, int /*version*/) int retval = 0; const XMLProperty* prop; + uint32_t bank; + bool active = _active; + + if ((prop = node.property (X_("ipmidi-base"))) != 0) { + set_ipmidi_base (atoi (prop->value())); + } // fetch current bank if ((prop = node.property (X_("bank"))) != 0) { - string bank = prop->value(); - set_active (true); - uint32_t new_bank = atoi (bank.c_str()); - if (_current_initial_bank != new_bank) { - switch_banks (new_bank); - } + bank = atoi (prop->value()); + } + + if ((prop = node.property (X_("active"))) != 0) { + active = string_is_affirmative (prop->value()); + } + + if ((prop = node.property (X_("device-name"))) != 0) { + set_device (prop->value()); + } + + if ((prop = node.property (X_("device-profile"))) != 0) { + set_profile (prop->value()); + } + + set_active (active); + + if (_active) { + switch_banks (bank, true); } return retval; @@ -1166,8 +1184,6 @@ MackieControlProtocol::force_special_route_to_strip (boost::shared_ptr r, void MackieControlProtocol::gui_track_selection_changed (ARDOUR::RouteNotificationListPtr rl) { - cerr << "GUI Selection changed, " << rl->size() << " routes\n"; - for (Surfaces::iterator s = surfaces.begin(); s != surfaces.end(); ++s) { (*s)->gui_selection_changed (rl); } @@ -1366,3 +1382,31 @@ MackieControlProtocol::pull_route_range (DownButtonList& down, RouteList& select } } } + +void +MackieControlProtocol::set_ipmidi_base (int16_t portnum) +{ + /* this will not be saved without a session save, so .. */ + + session->set_dirty (); + + _ipmidi_base = portnum; + + /* if the current device uses ipMIDI we need + to restart. + */ + + if (_active && _device_info.uses_ipmidi()) { + needs_ipmidi_restart = true; + } +} + +void +MackieControlProtocol::ipmidi_restart () +{ + clear_ports (); + surfaces.clear (); + create_surfaces (); + switch_banks (_current_initial_bank, true); + needs_ipmidi_restart = false; +} diff --git a/libs/surfaces/mackie/mackie_control_protocol.h b/libs/surfaces/mackie/mackie_control_protocol.h index ad01c2d1de..d092a372cd 100644 --- a/libs/surfaces/mackie/mackie_control_protocol.h +++ b/libs/surfaces/mackie/mackie_control_protocol.h @@ -192,6 +192,9 @@ class MackieControlProtocol void add_down_select_button (int surface, int strip); void remove_down_select_button (int surface, int strip); void select_range (); + + int16_t ipmidi_base() const { return _ipmidi_base; } + void set_ipmidi_base (int16_t); protected: // shut down the surface @@ -278,6 +281,8 @@ class MackieControlProtocol int _modifier_state; PortSources port_sources; ButtonMap button_map; + int16_t _ipmidi_base; + bool needs_ipmidi_restart; void create_surfaces (); bool periodic(); @@ -286,10 +291,9 @@ class MackieControlProtocol void clear_ports (); void force_special_route_to_strip (boost::shared_ptr r, uint32_t surface, uint32_t strip_number); void build_button_map (); - void gui_track_selection_changed (ARDOUR::RouteNotificationListPtr); - - + void ipmidi_restart (); + /* BUTTON HANDLING */ typedef std::set DownButtonList; diff --git a/libs/surfaces/mackie/surface_port.cc b/libs/surfaces/mackie/surface_port.cc index 77d71b1a6a..bf5e7417ab 100644 --- a/libs/surfaces/mackie/surface_port.cc +++ b/libs/surfaces/mackie/surface_port.cc @@ -56,7 +56,7 @@ SurfacePort::SurfacePort (Surface& s) , _output_port (0) { if (_surface->mcp().device_info().uses_ipmidi()) { - _input_port = new MIDI::IPMIDIPort (MIDI::IPMIDIPort::lowest_ipmidi_port_default+_surface->number()); + _input_port = new MIDI::IPMIDIPort (_surface->mcp().ipmidi_base() +_surface->number()); _output_port = _input_port; } else { jack_client_t* jack = MackieControlProtocol::instance()->get_session().engine().jack(); -- cgit v1.2.3