summaryrefslogtreecommitdiff
path: root/libs/ardour
diff options
context:
space:
mode:
authorPaul Davis <paul@linuxaudiosystems.com>2011-10-20 18:50:29 +0000
committerPaul Davis <paul@linuxaudiosystems.com>2011-10-20 18:50:29 +0000
commit3764eedca0d8ca8d666401c8bb8364705a64317e (patch)
treeeb666341e2b9a48c2cb8f2534725d6adfb33107e /libs/ardour
parent49b459f8d32ccabdac7cc0bacf3976557c00b2a6 (diff)
add initial implementation of explicit monitor (input|disk) control. some behaviour to be worked out, still
git-svn-id: svn://localhost/ardour2/branches/3.0@10256 d708f5d6-7413-0410-9779-e7cbd77b26cf
Diffstat (limited to 'libs/ardour')
-rw-r--r--libs/ardour/ardour/session.h17
-rw-r--r--libs/ardour/ardour/track.h11
-rw-r--r--libs/ardour/ardour/types.h7
-rw-r--r--libs/ardour/audio_track.cc10
-rw-r--r--libs/ardour/enums.cc7
-rw-r--r--libs/ardour/session_rtevents.cc25
-rw-r--r--libs/ardour/track.cc46
7 files changed, 85 insertions, 38 deletions
diff --git a/libs/ardour/ardour/session.h b/libs/ardour/ardour/session.h
index d96d8fc828..ad42ee768b 100644
--- a/libs/ardour/ardour/session.h
+++ b/libs/ardour/ardour/session.h
@@ -37,6 +37,7 @@
#include <glibmm/thread.h>
#include "pbd/error.h"
+#include "pbd/event_loop.h"
#include "pbd/rcu.h"
#include "pbd/statefuldestructible.h"
#include "pbd/signals.h"
@@ -622,6 +623,7 @@ class Session : public PBD::StatefulDestructible, public PBD::ScopedConnectionLi
void set_record_enabled (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
void set_solo_isolated (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
void set_exclusive_input_active (boost::shared_ptr<Route> rt, bool others_on);
+ void set_monitoring (boost::shared_ptr<RouteList>, MonitorChoice, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
PBD::Signal1<void,bool> SoloActive;
PBD::Signal0<void> SoloChanged;
@@ -1454,10 +1456,16 @@ class Session : public PBD::StatefulDestructible, public PBD::ScopedConnectionLi
static int ask_about_playlist_deletion (boost::shared_ptr<Playlist>);
/* realtime "apply to set of routes" operations */
- SessionEvent* get_rt_event (
- boost::shared_ptr<RouteList> rl, bool yn,
- SessionEvent::RTeventCallback after, bool group_override,
- void (Session::*method) (boost::shared_ptr<RouteList>, bool, bool));
+ template<typename T> SessionEvent*
+ get_rt_event (boost::shared_ptr<RouteList> rl, T targ, SessionEvent::RTeventCallback after, bool group_override,
+ void (Session::*method) (boost::shared_ptr<RouteList>, T, bool)) {
+ SessionEvent* ev = new SessionEvent (SessionEvent::RealTimeOperation, SessionEvent::Add, SessionEvent::Immediate, 0, 0.0);
+ ev->rt_slot = boost::bind (method, this, rl, targ, group_override);
+ ev->rt_return = after;
+ ev->event_loop = PBD::EventLoop::get_event_loop_for_thread ();
+
+ return ev;
+ }
void rt_set_solo (boost::shared_ptr<RouteList>, bool yn, bool group_override);
void rt_set_just_one_solo (boost::shared_ptr<RouteList>, bool yn, bool /* ignored*/ );
@@ -1465,6 +1473,7 @@ class Session : public PBD::StatefulDestructible, public PBD::ScopedConnectionLi
void rt_set_listen (boost::shared_ptr<RouteList>, bool yn, bool group_override);
void rt_set_solo_isolated (boost::shared_ptr<RouteList>, bool yn, bool group_override);
void rt_set_record_enabled (boost::shared_ptr<RouteList>, bool yn, bool group_override);
+ void rt_set_monitoring (boost::shared_ptr<RouteList>, MonitorChoice, bool group_override);
/** temporary list of Diskstreams used only during load of 2.X sessions */
std::list<boost::shared_ptr<Diskstream> > _diskstreams_2X;
diff --git a/libs/ardour/ardour/track.h b/libs/ardour/ardour/track.h
index 6e7d9ae1e5..9aefc4f403 100644
--- a/libs/ardour/ardour/track.h
+++ b/libs/ardour/ardour/track.h
@@ -48,6 +48,10 @@ class Track : public Route, public PublicDiskstream
virtual bool can_use_mode (TrackMode /*m*/, bool& /*bounce_required*/) { return false; }
PBD::Signal0<void> TrackModeChanged;
+ virtual void set_monitoring (MonitorChoice);
+ MonitorChoice monitoring() const { return _monitoring; }
+ PBD::Signal0<void> MonitoringChanged;
+
virtual int no_roll (pframes_t nframes, framepos_t start_frame, framepos_t end_frame,
bool state_changing, bool can_record);
@@ -161,9 +165,10 @@ class Track : public Route, public PublicDiskstream
virtual XMLNode& state (bool full) = 0;
boost::shared_ptr<Diskstream> _diskstream;
- MeterPoint _saved_meter_point;
- TrackMode _mode;
- bool _needs_butler;
+ MeterPoint _saved_meter_point;
+ TrackMode _mode;
+ bool _needs_butler;
+ MonitorChoice _monitoring;
//private: (FIXME)
struct FreezeRecordProcessorInfo {
diff --git a/libs/ardour/ardour/types.h b/libs/ardour/ardour/types.h
index 9579c87b7b..e2daf1a76c 100644
--- a/libs/ardour/ardour/types.h
+++ b/libs/ardour/ardour/types.h
@@ -358,6 +358,13 @@ namespace ARDOUR {
ExternalMonitoring
};
+ enum MonitorChoice {
+ MonitorAuto = 0,
+ MonitorInput = 0x1,
+ MonitorDisk = 0x2,
+ MonitorCue = 0x4,
+ };
+
enum PFLPosition {
/** PFL signals come from before pre-fader processors */
PFLFromBeforeProcessors,
diff --git a/libs/ardour/audio_track.cc b/libs/ardour/audio_track.cc
index 14870cb72d..b22b28d277 100644
--- a/libs/ardour/audio_track.cc
+++ b/libs/ardour/audio_track.cc
@@ -403,12 +403,16 @@ AudioTrack::roll (pframes_t nframes, framepos_t start_frame, framepos_t end_fram
_input->process_input (_meter, start_frame, end_frame, nframes);
}
- if (diskstream->record_enabled() && !can_record && !_session.config.get_auto_input()) {
-
+ if ((_monitoring & MonitorInput) ||
+ (!(_monitoring & MonitorDisk) &&
+ (diskstream->record_enabled() && !can_record && !_session.config.get_auto_input()))) {
+
/* not actually recording, but we want to hear the input material anyway,
at least potentially (depending on monitoring options)
*/
+ cerr << name() << " do the passthru thing with monitoring = " << enum_2_string (_monitoring) << endl;
+
passthru (start_frame, end_frame, nframes, false);
} else if ((b = diskstream->playback_buffer(0)) != 0) {
@@ -734,3 +738,5 @@ AudioTrack::bounceable () const
{
return n_inputs().n_audio() >= n_outputs().n_audio();
}
+
+
diff --git a/libs/ardour/enums.cc b/libs/ardour/enums.cc
index 8fd008c119..dc3a115bf5 100644
--- a/libs/ardour/enums.cc
+++ b/libs/ardour/enums.cc
@@ -66,6 +66,7 @@ setup_enum_writer ()
RegionPoint _RegionPoint;
Placement _Placement;
MonitorModel _MonitorModel;
+ MonitorChoice _MonitorChoice;
PFLPosition _PFLPosition;
AFLPosition _AFLPosition;
RemoteModel _RemoteModel;
@@ -228,6 +229,12 @@ setup_enum_writer ()
REGISTER_ENUM (ExternalMonitoring);
REGISTER (_MonitorModel);
+ REGISTER_ENUM (MonitorInput);
+ REGISTER_ENUM (MonitorDisk);
+ REGISTER_ENUM (MonitorAuto);
+ REGISTER_ENUM (MonitorCue);
+ REGISTER_BITS (_MonitorChoice);
+
REGISTER_ENUM (PFLFromBeforeProcessors);
REGISTER_ENUM (PFLFromAfterProcessors);
REGISTER (_PFLPosition);
diff --git a/libs/ardour/session_rtevents.cc b/libs/ardour/session_rtevents.cc
index ce40c5ce9e..ca1ee319c7 100644
--- a/libs/ardour/session_rtevents.cc
+++ b/libs/ardour/session_rtevents.cc
@@ -32,16 +32,25 @@ using namespace PBD;
using namespace ARDOUR;
using namespace Glib;
-SessionEvent*
-Session::get_rt_event (boost::shared_ptr<RouteList> rl, bool yn, SessionEvent::RTeventCallback after, bool group_override,
- void (Session::*method) (boost::shared_ptr<RouteList>, bool, bool))
+void
+Session::set_monitoring (boost::shared_ptr<RouteList> rl, MonitorChoice mc, SessionEvent::RTeventCallback after, bool group_override)
+{
+ queue_event (get_rt_event (rl, mc, after, group_override, &Session::rt_set_monitoring));
+}
+
+void
+Session::rt_set_monitoring (boost::shared_ptr<RouteList> rl, MonitorChoice mc, bool /* group_override */)
{
- SessionEvent* ev = new SessionEvent (SessionEvent::RealTimeOperation, SessionEvent::Add, SessionEvent::Immediate, 0, 0.0);
- ev->rt_slot = boost::bind (method, this, rl, yn, group_override);
- ev->rt_return = after;
- ev->event_loop = EventLoop::get_event_loop_for_thread ();
+ for (RouteList::iterator i = rl->begin(); i != rl->end(); ++i) {
+ if (!(*i)->is_hidden()) {
+ boost::shared_ptr<Track> t = boost::dynamic_pointer_cast<Track> (*i);
+ if (t) {
+ t->set_monitoring (mc);
+ }
+ }
+ }
- return ev;
+ set_dirty();
}
void
diff --git a/libs/ardour/track.cc b/libs/ardour/track.cc
index 5c9bcc747d..b21a02b490 100644
--- a/libs/ardour/track.cc
+++ b/libs/ardour/track.cc
@@ -43,6 +43,7 @@ Track::Track (Session& sess, string name, Route::Flag flag, TrackMode mode, Data
: Route (sess, name, flag, default_type)
, _saved_meter_point (_meter_point)
, _mode (mode)
+ , _monitoring (MonitorAuto)
, _rec_enable_control (new RecEnableControllable(*this))
{
_freeze_record.state = NoFreeze;
@@ -640,36 +641,31 @@ Track::adjust_capture_buffering ()
bool
Track::send_silence () const
{
- /*
- ADATs work in a strange way..
- they monitor input always when stopped.and auto-input is engaged.
-
- Other machines switch to input on stop if the track is record enabled,
- regardless of the auto input setting (auto input only changes the
- monitoring state when the transport is rolling)
- */
-
bool send_silence;
- if (!Config->get_tape_machine_mode()) {
- /*
- ADATs work in a strange way..
- they monitor input always when stopped.and auto-input is engaged.
+ if (Config->get_tape_machine_mode()) {
+
+ /* ADATs work in a strange way..
+ they monitor input always when stopped.and auto-input is engaged.
*/
+
if ((Config->get_monitoring_model() == SoftwareMonitoring)
- && (_session.config.get_auto_input () || _diskstream->record_enabled())) {
- send_silence = false;
+ && ((_monitoring & MonitorInput) || (_diskstream->record_enabled()))) {
+ send_silence = false;
} else {
send_silence = true;
}
+
+
} else {
- /*
- Other machines switch to input on stop if the track is record enabled,
- regardless of the auto input setting (auto input only changes the
- monitoring state when the transport is rolling)
+
+ /* Other machines switch to input on stop if the track is record enabled,
+ regardless of the auto input setting (auto input only changes the
+ monitoring state when the transport is rolling)
*/
+
if ((Config->get_monitoring_model() == SoftwareMonitoring)
- && _diskstream->record_enabled()) {
+ && (!(_monitoring & MonitorDisk) && (_session.config.get_auto_input () || _diskstream->record_enabled()))) {
send_silence = false;
} else {
send_silence = true;
@@ -732,6 +728,14 @@ Track::check_initial_delay (framecnt_t nframes, framecnt_t& transport_frame)
}
- return nframes;
+ return nframes;
}
+void
+Track::set_monitoring (MonitorChoice mc)
+{
+ if (mc != _monitoring) {
+ _monitoring = mc;
+ MonitoringChanged (); /* EMIT SIGNAL */
+ }
+}