X-Git-Url: https://main.carlh.net/gitweb/?a=blobdiff_plain;f=libs%2Fardour%2Fautomation_control.cc;h=3629345d941e7a9efe06fc805df15080ea07a939;hb=c7ff67004a51ae3f0453531c3d64bd9876f1df3b;hp=da33ad12a52ed1b21e8d8f187cd6a4cb33d47667;hpb=57ce447fd19bd794afe90748d466bbe172c2eab0;p=ardour.git diff --git a/libs/ardour/automation_control.cc b/libs/ardour/automation_control.cc index da33ad12a5..3629345d94 100644 --- a/libs/ardour/automation_control.cc +++ b/libs/ardour/automation_control.cc @@ -18,13 +18,26 @@ */ +#include #include - #include "ardour/automation_control.h" #include "ardour/automation_watch.h" #include "ardour/event_type_map.h" #include "ardour/session.h" +#include "pbd/memento_command.h" +#include "pbd/stacktrace.h" + +#include "i18n.h" + +#ifdef COMPILER_MSVC +#include +// C99 'isfinite()' is not available in MSVC. +#define isfinite_local(val) (bool)_finite((double)val) +#else +#define isfinite_local isfinite +#endif + using namespace std; using namespace ARDOUR; using namespace PBD; @@ -45,6 +58,16 @@ AutomationControl::~AutomationControl () { } +bool +AutomationControl::writable() const +{ + boost::shared_ptr al = alist(); + if (al) { + return al->automation_state() != Play; + } + return true; +} + /** Get the current effective `user' value based on automation state */ double AutomationControl::get_value() const @@ -58,7 +81,7 @@ AutomationControl::get_value() const * @param value `user' value */ void -AutomationControl::set_value (double value) +AutomationControl::set_value (double value, PBD::Controllable::GroupControlDisposition /* group_override */) { bool to_list = _list && ((AutomationList*)_list.get())->automation_write(); @@ -113,11 +136,15 @@ AutomationControl::set_automation_style (AutoStyle as) void AutomationControl::start_touch(double when) { - if (!_list) return; + if (!_list) { + return; + } + if (!touching()) { + if (alist()->automation_state() == Touch) { /* subtle. aligns the user value with the playback */ - set_value (get_value ()); + set_value (get_value (), Controllable::NoGroup); alist()->start_touch (when); if (!_desc.toggled) { AutomationWatch::instance().add_automation_watch (shared_from_this()); @@ -133,15 +160,30 @@ AutomationControl::stop_touch(bool mark, double when) if (!_list) return; if (touching()) { set_touching (false); + if (alist()->automation_state() == Touch) { alist()->stop_touch (mark, when); if (!_desc.toggled) { AutomationWatch::instance().remove_automation_watch (shared_from_this()); + } } } } +void +AutomationControl::commit_transaction (bool did_write) +{ + if (did_write) { + if (alist ()->before ()) { + _session.begin_reversible_command (string_compose (_("record %1 automation"), name ())); + _session.commit_reversible_command (new MementoCommand (*alist ().get (), alist ()->before (), &alist ()->get_state ())); + } + } else { + alist ()->clear_history (); + } +} + double AutomationControl::internal_to_interface (double val) const { @@ -154,7 +196,7 @@ AutomationControl::internal_to_interface (double val) const if (_desc.logarithmic) { if (val > 0) { - val = pow (val, 1/1.5); + val = pow (val, 1./2.0); } else { val = 0; } @@ -166,11 +208,14 @@ AutomationControl::internal_to_interface (double val) const double AutomationControl::interface_to_internal (double val) const { + if (!isfinite_local (val)) { + val = 0; + } if (_desc.logarithmic) { if (val <= 0) { val = 0; } else { - val = pow (val, 1.5); + val = pow (val, 2.0); } }