From 2177f008411821e7bce9ca3c306ec64c70b1c58e Mon Sep 17 00:00:00 2001 From: David Robillard Date: Wed, 4 Jul 2007 00:39:00 +0000 Subject: [PATCH] Add AutomationControl::parameter() for terseness. Future-proof automation track GUI 'extra' XML ( instead of so Parameter.to_string isn't used as an XML node name). Fix automation track controller bar shown/hidden state. Fix automation track initial show bug. git-svn-id: svn://localhost/ardour2/trunk@2103 d708f5d6-7413-0410-9779-e7cbd77b26cf --- gtk2_ardour/audio_time_axis.cc | 43 ++--- gtk2_ardour/audio_time_axis.h | 4 +- gtk2_ardour/automation_controller.cc | 2 +- gtk2_ardour/automation_time_axis.cc | 198 ++++++++++-------------- gtk2_ardour/automation_time_axis.h | 9 +- gtk2_ardour/editor.cc | 6 +- gtk2_ardour/midi_time_axis.cc | 9 +- gtk2_ardour/midi_time_axis.h | 2 +- gtk2_ardour/plugin_ui.h | 2 +- gtk2_ardour/route_time_axis.cc | 39 +++-- gtk2_ardour/route_time_axis.h | 6 +- gtk2_ardour/route_ui.cc | 35 +++-- gtk2_ardour/route_ui.h | 2 +- gtk2_ardour/time_axis_view.h | 3 +- libs/ardour/ardour/automation_control.h | 3 + libs/ardour/ardour/midi_buffer.h | 2 + libs/ardour/audiofilesource.cc | 6 +- libs/ardour/automatable.cc | 2 +- libs/ardour/automation_control.cc | 6 + libs/ardour/automation_event.cc | 8 +- libs/ardour/location.cc | 2 +- libs/ardour/plugin_insert.cc | 2 +- libs/ardour/session_state.cc | 2 +- libs/ardour/session_timefx.cc | 2 +- 24 files changed, 179 insertions(+), 216 deletions(-) diff --git a/gtk2_ardour/audio_time_axis.cc b/gtk2_ardour/audio_time_axis.cc index 0b20c007ef..73500f3ea1 100644 --- a/gtk2_ardour/audio_time_axis.cc +++ b/gtk2_ardour/audio_time_axis.cc @@ -85,8 +85,7 @@ AudioTimeAxisView::AudioTimeAxisView (PublicEditor& ed, Session& sess, boost::sh _view = new AudioStreamView (*this); - create_automation_child (GainAutomation); - create_automation_child (PanAutomation); + create_automation_child (GainAutomation, false); ignore_toggle = false; @@ -107,7 +106,7 @@ AudioTimeAxisView::AudioTimeAxisView (PublicEditor& ed, Session& sess, boost::sh set_state (*xml_node); - _route->panner().Changed.connect (mem_fun(*this, &AudioTimeAxisView::update_pans)); + _route->panner().Changed.connect (bind (mem_fun(*this, &AudioTimeAxisView::update_pans), false)); update_control_names (); @@ -279,7 +278,7 @@ AudioTimeAxisView::set_waveform_scale (WaveformScale scale) } void -AudioTimeAxisView::create_automation_child (Parameter param) +AudioTimeAxisView::create_automation_child (Parameter param, bool show) { if (param.type() == GainAutomation) { @@ -294,15 +293,14 @@ AudioTimeAxisView::create_automation_child (Parameter param) editor, *this, parent_canvas, - _route->describe_parameter(param), - c->list()->parameter().to_string() /* FIXME: correct state name? */)); + _route->describe_parameter(param))); - add_automation_child(Parameter(GainAutomation), gain_track); + add_automation_child(Parameter(GainAutomation), gain_track, show); } else if (param.type() == PanAutomation) { ensure_xml_node (); - update_pans (); + update_pans (show); } else { error << "AudioTimeAxisView: unknown automation child " << param.to_string() << endmsg; @@ -310,35 +308,15 @@ AudioTimeAxisView::create_automation_child (Parameter param) } void -AudioTimeAxisView::update_pans () +AudioTimeAxisView::update_pans (bool show) { Panner::iterator p; - /* This is a filthy kludge until the panner stuff gets up to speed. */ - - /* Remove all our old automation tracks. Slowly. */ - /*while (true) { - bool found = false; - for (AutomationTracks::iterator i = _automation_tracks.begin(); i != _automation_tracks.end(); ++i) { - if (i->first.type() == PanAutomation) { - remove_child(i->second->track); - delete i->second; - _automation_tracks.erase(i); - found = true; - break; - } - } - - if ( ! found) - break; - }*/ - - /* Man I hate that damn stereo->stereo panner */ uint32_t i = 0; for (p = _route->panner().begin(); p != _route->panner().end(); ++p) { boost::shared_ptr pan_control = (*p)->pan_control(); - if (pan_control->list()->parameter().type() == NullAutomation) { + if (pan_control->parameter().type() == NullAutomation) { error << "Pan control has NULL automation type!" << endmsg; continue; } @@ -348,9 +326,8 @@ AudioTimeAxisView::update_pans () editor, *this, parent_canvas, - _route->describe_parameter(pan_control->list()->parameter()), - pan_control->list()->parameter().to_string()/* FIXME: correct state name? */)); - add_automation_child(Parameter(PanAutomation, i), pan_track); + _route->describe_parameter(pan_control->parameter()))); + add_automation_child(Parameter(PanAutomation, i), pan_track, show); ++i; } } diff --git a/gtk2_ardour/audio_time_axis.h b/gtk2_ardour/audio_time_axis.h index f903559e98..b0183e5e19 100644 --- a/gtk2_ardour/audio_time_axis.h +++ b/gtk2_ardour/audio_time_axis.h @@ -82,7 +82,7 @@ class AudioTimeAxisView : public RouteTimeAxisView guint32 show_at (double y, int& nth, Gtk::VBox *parent); void hide (); - void create_automation_child (ARDOUR::Parameter param); + void create_automation_child (ARDOUR::Parameter param, bool show); private: friend class AudioStreamView; @@ -104,7 +104,7 @@ class AudioTimeAxisView : public RouteTimeAxisView void gain_hidden (); void pan_hidden (); - void update_pans (); + void update_pans (bool show=true); void update_control_names (); Gtk::CheckMenuItem* waveform_item; diff --git a/gtk2_ardour/automation_controller.cc b/gtk2_ardour/automation_controller.cc index 56ace4db32..09d1f1e744 100644 --- a/gtk2_ardour/automation_controller.cc +++ b/gtk2_ardour/automation_controller.cc @@ -76,7 +76,7 @@ AutomationController::update_label(char* label, int label_len) { if (label && label_len) // Hack to display CC rounded to int - if (_controllable->list()->parameter().type() == MidiCCAutomation) + if (_controllable->parameter().type() == MidiCCAutomation) snprintf(label, label_len, "%d", (int)_controllable->get_value()); else snprintf(label, label_len, "%.3f", _controllable->get_value()); diff --git a/gtk2_ardour/automation_time_axis.cc b/gtk2_ardour/automation_time_axis.cc index 8170c42cd5..28d8ba326f 100644 --- a/gtk2_ardour/automation_time_axis.cc +++ b/gtk2_ardour/automation_time_axis.cc @@ -25,6 +25,7 @@ #include "ardour_ui.h" #include "automation_time_axis.h" +#include "route_time_axis.h" #include "automation_line.h" #include "public_editor.h" #include "simplerect.h" @@ -46,12 +47,12 @@ using namespace Editing; Pango::FontDescription* AutomationTimeAxisView::name_font = 0; bool AutomationTimeAxisView::have_name_font = false; +const string AutomationTimeAxisView::state_node_name = "AutomationChild"; AutomationTimeAxisView::AutomationTimeAxisView (Session& s, boost::shared_ptr r, boost::shared_ptr a, boost::shared_ptr c, PublicEditor& e, TimeAxisView& rent, - ArdourCanvas::Canvas& canvas, const string & nom, - const string & state_name, const string & nomparent) + ArdourCanvas::Canvas& canvas, const string & nom, const string & nomparent) : AxisView (s), TimeAxisView (s, e, &rent, canvas), @@ -60,9 +61,7 @@ AutomationTimeAxisView::AutomationTimeAxisView (Session& s, boost::shared_ptrlist(), c)), _base_rect (0), - _xml_node (0), _name (nom), - _state_name (state_name), height_button (_("h")), clear_button (_("clear")), auto_button (X_("")) /* force addition of a label */ @@ -187,14 +186,15 @@ AutomationTimeAxisView::AutomationTimeAxisView (Session& s, boost::shared_ptrget_child_xml_node (_state_name); + XMLNode* xml_node = get_parent_with_state()->get_automation_child_xml_node ( + _control->parameter()); if (xml_node) { set_state (*xml_node); } boost::shared_ptr line(new AutomationLine ( - _control->list()->parameter().to_string(), + _control->parameter().to_string(), *this, *canvas_display, _control->list())); @@ -247,7 +247,7 @@ AutomationTimeAxisView::set_automation_state (AutoState state) if (!ignore_state_request) { if (_route == _automatable) { // FIXME: ew _route->set_parameter_automation_state ( - _control->list()->parameter(), + _control->parameter(), state); } @@ -338,12 +338,10 @@ void AutomationTimeAxisView::set_height (TrackHeight ht) { uint32_t h = height_to_pixels (ht); - bool changed = (height != (uint32_t) h); - - //bool changed_between_small_and_normal = ( (ht == Small || ht == Smaller) ^ (height_style == Small || height_style == Smaller) ); - - TimeAxisView* state_parent = get_parent_with_state (); - XMLNode* xml_node = state_parent->get_child_xml_node (_state_name); + bool changed = (height != (uint32_t) h) || first_call_to_set_height; + + if (first_call_to_set_height) + first_call_to_set_height = false; TimeAxisView::set_height (ht); _base_rect->property_y2() = h; @@ -355,6 +353,11 @@ AutomationTimeAxisView::set_height (TrackHeight ht) (*i)->set_height (); } + TimeAxisView* state_parent = get_parent_with_state (); + assert(state_parent); + + XMLNode* xml_node = state_parent->get_automation_child_xml_node(_control->parameter()); + assert(xml_node); switch (ht) { case Largest: @@ -382,67 +385,63 @@ AutomationTimeAxisView::set_height (TrackHeight ht) break; } - //if (changed_between_small_and_normal || first_call_to_set_height) { - first_call_to_set_height = false; - switch (ht) { - case Normal: + switch (ht) { + case Large: + case Larger: + case Largest: + _controller->show (); + + case Normal: + if (ht == Normal) _controller->hide(); - controls_table.remove (name_hbox); + controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } - controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - plugname_packed = true; - controls_table.attach (name_hbox, 1, 5, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } else { - controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - } - hide_name_entry (); - show_name_label (); - name_hbox.show_all (); - - auto_button.show(); - height_button.show(); - clear_button.show(); - hide_button.show_all(); - break; - - case Large: - case Larger: - case Largest: - _controller->show (); - break; - - case Smaller: - _controller->hide(); - - case Small: - - controls_table.remove (name_hbox); - if (plugname) { - if (plugname_packed) { - controls_table.remove (*plugname); - plugname_packed = false; - } + if (plugname) { + if (plugname_packed) { + controls_table.remove (*plugname); + plugname_packed = false; } + controls_table.attach (*plugname, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + plugname_packed = true; + controls_table.attach (name_hbox, 1, 5, 1, 2, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + } else { controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); - controls_table.hide_all (); - hide_name_entry (); - show_name_label (); - name_hbox.show_all (); + } + hide_name_entry (); + show_name_label (); + name_hbox.show_all (); - auto_button.hide(); - height_button.hide(); - clear_button.hide(); - hide_button.hide(); - break; - } + auto_button.show(); + height_button.show(); + clear_button.show(); + hide_button.show_all(); + break; - //} + case Smaller: + _controller->hide(); + + case Small: + + controls_table.remove (name_hbox); + if (plugname) { + if (plugname_packed) { + controls_table.remove (*plugname); + plugname_packed = false; + } + } + controls_table.attach (name_hbox, 1, 5, 0, 1, Gtk::FILL|Gtk::EXPAND, Gtk::FILL|Gtk::EXPAND); + controls_table.hide_all (); + hide_name_entry (); + show_name_label (); + name_hbox.show_all (); + + auto_button.hide(); + height_button.hide(); + clear_button.hide(); + hide_button.hide(); + break; + } if (changed) { /* only emit the signal if the height really changed */ @@ -866,25 +865,25 @@ AutomationTimeAxisView::set_state (const XMLNode& node) kids = node.children (); - //snprintf (buf, sizeof(buf), "Port_%" PRIu32, param.id()); - for (iter = kids.begin(); iter != kids.end(); ++iter) { - if ((*iter)->name() == _control->list()->parameter().to_string()) { - XMLProperty *shown = (*iter)->property("shown_editor"); - - if (shown && shown->value() == "yes") { - set_marked_for_display(true); - canvas_display->show(); /* FIXME: necessary? show_at? */ + if ((*iter)->name() == state_node_name) { + XMLProperty* type = (*iter)->property("automation-id"); + + if (type && type->value() == _control->parameter().to_string()) { + XMLProperty *shown = (*iter)->property("shown_editor"); + + if (shown && shown->value() == "yes") { + set_marked_for_display(true); + canvas_display->show(); /* FIXME: necessary? show_at? */ + } + break; } - break; } } if (!_marked_for_display) hide(); - - // FIXME: _xml_node = &node? } XMLNode* @@ -893,54 +892,17 @@ AutomationTimeAxisView::get_state_node () TimeAxisView* state_parent = get_parent_with_state (); if (state_parent) { - return state_parent->get_child_xml_node (_state_name); + return state_parent->get_automation_child_xml_node (_control->parameter()); } else { return 0; } } -void -AutomationTimeAxisView::ensure_xml_node () -{ - if ((_automatable != _route) && _xml_node == 0) { - if ((_xml_node = _automatable->extra_xml ("GUI")) == 0) { - _xml_node = new XMLNode ("GUI"); - _automatable->add_extra_xml (*_xml_node); - } - } -} - void AutomationTimeAxisView::update_extra_xml_shown (bool editor_shown) { - if (_automatable == _route) - return; - - char buf[32]; - - ensure_xml_node (); - - XMLNodeList nlist = _xml_node->children (); - XMLNodeConstIterator i; - XMLNode * port_node = 0; - - /* FIXME: these parsed XML node names need to go */ - //snprintf (buf, sizeof(buf), "Port_%" PRIu32, _param.id()); - - for (i = nlist.begin(); i != nlist.end(); ++i) { - /* FIXME: legacy session loading */ - if ((*i)->name() == _control->list()->parameter().to_string()) { - port_node = (*i); - break; - } - } - - if (!port_node) { - port_node = new XMLNode(buf); - _xml_node->add_child_nocopy(*port_node); - } - - port_node->add_property ("shown_editor", editor_shown ? "yes": "no"); + XMLNode* xml_node = get_state_node(); + xml_node->add_property ("shown", editor_shown ? "yes" : "no"); } guint32 diff --git a/gtk2_ardour/automation_time_axis.h b/gtk2_ardour/automation_time_axis.h index a52db758b8..c3be6ffd00 100644 --- a/gtk2_ardour/automation_time_axis.h +++ b/gtk2_ardour/automation_time_axis.h @@ -64,7 +64,6 @@ class AutomationTimeAxisView : public TimeAxisView { TimeAxisView& parent, ArdourCanvas::Canvas& canvas, const string & name, /* translatable */ - const string & state_name, /* not translatable */ const string & plug_name = ""); ~AutomationTimeAxisView(); @@ -98,10 +97,12 @@ class AutomationTimeAxisView : public TimeAxisView { void show_all_control_points (); void hide_all_but_selected_control_points (); void set_state (const XMLNode&); - XMLNode* get_state_node (); guint32 show_at (double y, int& nth, Gtk::VBox *parent); void hide (); + + static const string state_node_name; + XMLNode* get_state_node(); protected: boost::shared_ptr _route; ///< Parent route @@ -113,10 +114,7 @@ class AutomationTimeAxisView : public TimeAxisView { ArdourCanvas::SimpleRect* _base_rect; boost::shared_ptr _line; - XMLNode* _xml_node; - string _name; - string _state_name; bool in_destructor; bool ignore_toggle; @@ -157,7 +155,6 @@ class AutomationTimeAxisView : public TimeAxisView { void automation_state_changed (); sigc::connection automation_connection; - void ensure_xml_node (); void update_extra_xml_shown (bool editor_shown); void entered (); diff --git a/gtk2_ardour/editor.cc b/gtk2_ardour/editor.cc index 690dc9058b..7ba3d9c537 100644 --- a/gtk2_ardour/editor.cc +++ b/gtk2_ardour/editor.cc @@ -1153,7 +1153,7 @@ Editor::connect_to_session (Session *t) if (ARDOUR_UI::instance()->session_is_new ()) { - TreeModel::Children rows = route_display_model->children(); + TreeModel::Children rows = route_display_model->children(); TreeModel::Children::iterator i; no_route_list_redisplay = true; @@ -1173,9 +1173,9 @@ Editor::connect_to_session (Session *t) redisplay_route_list (); } - /* register for undo history */ + /* register for undo history */ - session->register_with_memento_command_factory(_id, this); + session->register_with_memento_command_factory(_id, this); } void diff --git a/gtk2_ardour/midi_time_axis.cc b/gtk2_ardour/midi_time_axis.cc index 62eec3661a..d7864933b0 100644 --- a/gtk2_ardour/midi_time_axis.cc +++ b/gtk2_ardour/midi_time_axis.cc @@ -179,11 +179,11 @@ MidiTimeAxisView::add_controller_track() } if (response == Gtk::RESPONSE_ACCEPT) - create_automation_child(param); + create_automation_child(param, true); } void -MidiTimeAxisView::create_automation_child (Parameter param) +MidiTimeAxisView::create_automation_child (Parameter param, bool show) { if (param.type() == MidiCCAutomation) { @@ -202,10 +202,9 @@ MidiTimeAxisView::create_automation_child (Parameter param) editor, *this, parent_canvas, - _route->describe_parameter(param), - c->list()->parameter().to_string() /* FIXME: correct state name? */)); + _route->describe_parameter(param))); - add_automation_child(param, track); + add_automation_child(param, track, show); } else { error << "MidiTimeAxisView: unknown automation child " << param.to_string() << endmsg; diff --git a/gtk2_ardour/midi_time_axis.h b/gtk2_ardour/midi_time_axis.h index 34074b15d9..e25ab22de7 100644 --- a/gtk2_ardour/midi_time_axis.h +++ b/gtk2_ardour/midi_time_axis.h @@ -61,7 +61,7 @@ class MidiTimeAxisView : public RouteTimeAxisView void hide (); void add_controller_track (); - void create_automation_child (ARDOUR::Parameter param); + void create_automation_child (ARDOUR::Parameter param, bool show); private: diff --git a/gtk2_ardour/plugin_ui.h b/gtk2_ardour/plugin_ui.h index 6b1ead881e..17d643f2a1 100644 --- a/gtk2_ardour/plugin_ui.h +++ b/gtk2_ardour/plugin_ui.h @@ -144,7 +144,7 @@ class LadspaPluginUI : public PlugUIBase, public Gtk::VBox boost::shared_ptr control; - ARDOUR::Parameter parameter() { return control->list()->parameter(); } + ARDOUR::Parameter parameter() { return control->parameter(); } /* input */ diff --git a/gtk2_ardour/route_time_axis.cc b/gtk2_ardour/route_time_axis.cc index 596f84c249..976a3e1667 100644 --- a/gtk2_ardour/route_time_axis.cc +++ b/gtk2_ardour/route_time_axis.cc @@ -276,29 +276,36 @@ RouteTimeAxisView::set_state (const XMLNode& node) for (niter = nlist.begin(); niter != nlist.end(); ++niter) { child_node = *niter; + + if (child_node->name() != AutomationTimeAxisView::state_node_name) + continue; + + XMLProperty* prop = child_node->property ("automation-id"); + if (!prop) + continue; + + Parameter param(prop->value()); + if (!param) + continue; - Parameter param(child_node->name()); + bool show = false; - if (param) { - - XMLProperty* prop = child_node->property ("shown"); - - if (_automation_tracks.find(param) == _automation_tracks.end()) - create_automation_child(param); + prop = child_node->property ("shown"); - if (prop != 0 && prop->value() == "yes") - _show_automation.insert(Parameter(GainAutomation)); - - } else { - warning << "GUI info exists, but no parameter " << child_node->name() << " found." << endmsg; + if (prop && prop->value() == "yes") { + show = true; + _show_automation.insert(param); } + + if (_automation_tracks.find(param) == _automation_tracks.end()) + create_automation_child(param, show); } } XMLNode* -RouteTimeAxisView::get_child_xml_node (const string & childname) +RouteTimeAxisView::get_automation_child_xml_node (Parameter param) { - return RouteUI::get_child_xml_node (childname); + return RouteUI::get_automation_child_xml_node (param); } gint @@ -1767,7 +1774,7 @@ RouteTimeAxisView::add_existing_processor_automation_curves (boost::shared_ptr

track) +RouteTimeAxisView::add_automation_child(Parameter param, boost::shared_ptr track, bool show) { using namespace Menu_Helpers; @@ -1777,7 +1784,7 @@ RouteTimeAxisView::add_automation_child(Parameter param, boost::shared_ptrHiding.connect (bind (mem_fun (*this, &RouteTimeAxisView::automation_track_hidden), param)); - bool hideit = false; + bool hideit = (!show); XMLNode* node; diff --git a/gtk2_ardour/route_time_axis.h b/gtk2_ardour/route_time_axis.h index c412374fbd..0a6c3f0173 100644 --- a/gtk2_ardour/route_time_axis.h +++ b/gtk2_ardour/route_time_axis.h @@ -95,7 +95,7 @@ public: void build_playlist_menu (Gtk::Menu *); - virtual void create_automation_child (ARDOUR::Parameter param) = 0; + virtual void create_automation_child (ARDOUR::Parameter param, bool show) = 0; string name() const; StreamView* view() const { return _view; } @@ -169,7 +169,7 @@ protected: void add_processor_automation_curve (boost::shared_ptr r, ARDOUR::Parameter); void add_existing_processor_automation_curves (boost::shared_ptr); - void add_automation_child(ARDOUR::Parameter param, boost::shared_ptr track); + void add_automation_child(ARDOUR::Parameter param, boost::shared_ptr track, bool show=true); void reset_processor_automation_curves (); @@ -273,7 +273,7 @@ protected: void set_state (const XMLNode&); - XMLNode* get_child_xml_node (const string & childname); + XMLNode* get_automation_child_xml_node (ARDOUR::Parameter param); }; #endif /* __ardour_route_time_axis_h__ */ diff --git a/gtk2_ardour/route_ui.cc b/gtk2_ardour/route_ui.cc index 76c4b7b5b3..277ec12879 100644 --- a/gtk2_ardour/route_ui.cc +++ b/gtk2_ardour/route_ui.cc @@ -37,6 +37,7 @@ #include "gui_thread.h" #include "ardour_dialog.h" #include "latency_gui.h" +#include "automation_time_axis.h" #include #include @@ -648,10 +649,10 @@ void RouteUI::reversibly_apply_route_boolean (string name, void (Route::*func)(bool, void *), bool yn, void *arg) { _session.begin_reversible_command (name); - XMLNode &before = _route->get_state(); - bind(mem_fun(*_route, func), yn, arg)(); - XMLNode &after = _route->get_state(); - _session.add_command (new MementoCommand(*_route, &before, &after)); + XMLNode &before = _route->get_state(); + bind(mem_fun(*_route, func), yn, arg)(); + XMLNode &after = _route->get_state(); + _session.add_command (new MementoCommand(*_route, &before, &after)); _session.commit_reversible_command (); } @@ -659,9 +660,9 @@ void RouteUI::reversibly_apply_track_boolean (string name, void (Track::*func)(bool, void *), bool yn, void *arg) { _session.begin_reversible_command (name); - XMLNode &before = track()->get_state(); + XMLNode &before = track()->get_state(); bind (mem_fun (*track(), func), yn, arg)(); - XMLNode &after = track()->get_state(); + XMLNode &after = track()->get_state(); _session.add_command (new MementoCommand(*track(), &before, &after)); _session.commit_reversible_command (); } @@ -743,18 +744,26 @@ RouteUI::ensure_xml_node () } XMLNode* -RouteUI::get_child_xml_node (const string & childname) +RouteUI::get_automation_child_xml_node (Parameter param) { - XMLNode* child; - ensure_xml_node (); - - if ((child = find_named_node (*xml_node, childname)) == 0) { - child = new XMLNode (childname); - xml_node->add_child_nocopy (*child); + XMLNodeList kids = xml_node->children(); + XMLNodeConstIterator iter; + + for (iter = kids.begin(); iter != kids.end(); ++iter) { + if ((*iter)->name() == AutomationTimeAxisView::state_node_name) { + XMLProperty* type = (*iter)->property("automation-id"); + if (type && type->value() == param.to_string()) + return *iter; + } } + // Didn't find it, make a new one + XMLNode* child = new XMLNode (AutomationTimeAxisView::state_node_name); + child->add_property("automation-id", param.to_string()); + xml_node->add_child_nocopy (*child); + return child; } diff --git a/gtk2_ardour/route_ui.h b/gtk2_ardour/route_ui.h index 730330372a..20ac152f83 100644 --- a/gtk2_ardour/route_ui.h +++ b/gtk2_ardour/route_ui.h @@ -86,7 +86,7 @@ class RouteUI : public virtual AxisView XMLNode *xml_node; void ensure_xml_node (); - XMLNode* get_child_xml_node (const string & childname); + virtual XMLNode* get_automation_child_xml_node (ARDOUR::Parameter param); bool mute_press(GdkEventButton*); bool mute_release(GdkEventButton*); diff --git a/gtk2_ardour/time_axis_view.h b/gtk2_ardour/time_axis_view.h index 722350594a..62590c1d23 100644 --- a/gtk2_ardour/time_axis_view.h +++ b/gtk2_ardour/time_axis_view.h @@ -34,6 +34,7 @@ #include #include +#include #include "prompter.h" #include "axis_view.h" @@ -208,7 +209,7 @@ class TimeAxisView : public virtual AxisView /* call this on the parent */ - virtual XMLNode* get_child_xml_node (const string & childname) { return 0; } + virtual XMLNode* get_automation_child_xml_node (ARDOUR::Parameter param) { return 0; } typedef std::vector > Children; diff --git a/libs/ardour/ardour/automation_control.h b/libs/ardour/ardour/automation_control.h index 5810ced9f9..cc0aee5326 100644 --- a/libs/ardour/ardour/automation_control.h +++ b/libs/ardour/ardour/automation_control.h @@ -23,6 +23,7 @@ #include #include +#include namespace ARDOUR { @@ -47,6 +48,8 @@ public: boost::shared_ptr list() { return _list; } boost::shared_ptr list() const { return _list; } + Parameter parameter() const; + protected: ARDOUR::Session& _session; boost::shared_ptr _list; diff --git a/libs/ardour/ardour/midi_buffer.h b/libs/ardour/ardour/midi_buffer.h index ecb48d9da9..f7223fcecd 100644 --- a/libs/ardour/ardour/midi_buffer.h +++ b/libs/ardour/ardour/midi_buffer.h @@ -54,6 +54,8 @@ private: * (_size * MAX_EVENT_SIZE) */ + /* FIXME: this is utter crap. rewrite as a flat/packed buffer like MidiRingBuffer */ + MidiEvent* _events; ///< Event structs that point to offsets in _data Byte* _data; ///< MIDI, straight up. No time stamps. }; diff --git a/libs/ardour/audiofilesource.cc b/libs/ardour/audiofilesource.cc index 4bbe28e251..140f787901 100644 --- a/libs/ardour/audiofilesource.cc +++ b/libs/ardour/audiofilesource.cc @@ -228,7 +228,7 @@ AudioFileSource::set_state (const XMLNode& node) } if ((prop = node.property (X_("channel"))) != 0) { - _channel = atoi (prop->value()); + _channel = atoi (prop->value().c_str()); } else { _channel = 0; } @@ -433,7 +433,7 @@ AudioFileSource::find (ustring& pathstr, bool must_exist, bool& isnew, uint16_t& fullpath += shorter; if (Glib::file_test (pathstr, Glib::FILE_TEST_EXISTS|Glib::FILE_TEST_IS_REGULAR)) { - chan = atoi (pathstr.substr (pos+1)); + chan = atoi (pathstr.substr (pos+1).c_str()); pathstr = shorter; keeppath = fullpath; ++cnt; @@ -485,7 +485,7 @@ AudioFileSource::find (ustring& pathstr, bool must_exist, bool& isnew, uint16_t& ustring shorter = pathstr.substr (0, pos); if (Glib::file_test (shorter, Glib::FILE_TEST_EXISTS|Glib::FILE_TEST_IS_REGULAR)) { - chan = atoi (pathstr.substr (pos+1)); + chan = atoi (pathstr.substr (pos+1).c_str()); pathstr = shorter; } } diff --git a/libs/ardour/automatable.cc b/libs/ardour/automatable.cc index 4ca85a673c..14bccba056 100644 --- a/libs/ardour/automatable.cc +++ b/libs/ardour/automatable.cc @@ -121,7 +121,7 @@ Automatable::load_automation (const string& path) void Automatable::add_control(boost::shared_ptr ac) { - Parameter param = ac->list()->parameter(); + Parameter param = ac->parameter(); _controls[param] = ac; diff --git a/libs/ardour/automation_control.cc b/libs/ardour/automation_control.cc index 3ddf4172e8..bbeec65669 100644 --- a/libs/ardour/automation_control.cc +++ b/libs/ardour/automation_control.cc @@ -83,3 +83,9 @@ AutomationControl::set_list(boost::shared_ptr list) Changed(); /* EMIT SIGNAL */ } + +Parameter +AutomationControl::parameter() const +{ + return _list->parameter(); +} diff --git a/libs/ardour/automation_event.cc b/libs/ardour/automation_event.cc index 6fc24c7960..b7a4bc0399 100644 --- a/libs/ardour/automation_event.cc +++ b/libs/ardour/automation_event.cc @@ -1374,7 +1374,7 @@ AutomationList::set_state (const XMLNode& node) } if ((prop = node.property (X_("default"))) != 0){ - _default_value = atof (prop->value()); + _default_value = atof (prop->value().c_str()); } else { _default_value = 0.0; } @@ -1392,19 +1392,19 @@ AutomationList::set_state (const XMLNode& node) } if ((prop = node.property (X_("min_yval"))) != 0) { - _min_yval = atof (prop->value ()); + _min_yval = atof (prop->value ().c_str()); } else { _min_yval = FLT_MIN; } if ((prop = node.property (X_("max_yval"))) != 0) { - _max_yval = atof (prop->value ()); + _max_yval = atof (prop->value ().c_str()); } else { _max_yval = FLT_MAX; } if ((prop = node.property (X_("max_xval"))) != 0) { - _max_xval = atof (prop->value ()); + _max_xval = atof (prop->value ().c_str()); } else { _max_xval = 0; // means "no limit ; } diff --git a/libs/ardour/location.cc b/libs/ardour/location.cc index 3d04c66824..bd9e7b8af5 100644 --- a/libs/ardour/location.cc +++ b/libs/ardour/location.cc @@ -422,7 +422,7 @@ Locations::next_available_name(string& result,string base) location =* i; temp = location->name(); if (l && !temp.find(base,0)) { - suffix = atoi(temp.substr(l,3)); + suffix = atoi(temp.substr(l,3).c_str()); if (suffix) available[suffix] = false; } } diff --git a/libs/ardour/plugin_insert.cc b/libs/ardour/plugin_insert.cc index 31436254c5..1859c5405f 100644 --- a/libs/ardour/plugin_insert.cc +++ b/libs/ardour/plugin_insert.cc @@ -279,7 +279,7 @@ PluginInsert::connect_and_run (BufferSet& bufs, nframes_t nframes, nframes_t off boost::shared_ptr c = li->second; - if (c->list()->parameter().type() == PluginAutomation && c->list()->automation_playback()) { + if (c->parameter().type() == PluginAutomation && c->list()->automation_playback()) { bool valid; const float val = c->list()->rt_safe_eval (now, valid); diff --git a/libs/ardour/session_state.cc b/libs/ardour/session_state.cc index 2924210e0c..94aae01a53 100644 --- a/libs/ardour/session_state.cc +++ b/libs/ardour/session_state.cc @@ -707,7 +707,7 @@ Session::load_state (string snapshot_name) is_old = true; } else { int major_version; - major_version = atoi (prop->value()); // grab just the first number before the period + major_version = atoi (prop->value().c_str()); // grab just the first number before the period if (major_version < 2) { is_old = true; } diff --git a/libs/ardour/session_timefx.cc b/libs/ardour/session_timefx.cc index 4061b2ccd0..aac77a59c7 100644 --- a/libs/ardour/session_timefx.cc +++ b/libs/ardour/session_timefx.cc @@ -192,7 +192,7 @@ Session::tempoize_region (TimeStretchRequest& tsr) } else { if (tsr.region->name()[len] == 't') { - c = atoi (tsr.region->name().substr(len+1)); + c = atoi (tsr.region->name().substr(len+1).c_str()); snprintf (buf, sizeof (buf), "t%03d", ++c); region_name = tsr.region->name().substr (0, len) + buf;