Move a few declarations to first use.
[ardour.git] / libs / ardour / panner_shell.cc
index 762d0687d1c3a59c1246f5778441b9ad423403dc..fc72a27b09ea71b4b87c3d2fc8dc1cda1d01e87f 100644 (file)
@@ -53,6 +53,7 @@
 #include "ardour/panner_shell.h"
 #include "ardour/runtime_functions.h"
 #include "ardour/session.h"
+#include "ardour/speakers.h"
 #include "ardour/utils.h"
 
 #include "i18n.h"
@@ -66,13 +67,14 @@ using namespace PBD;
 PannerShell::PannerShell (string name, Session& s, boost::shared_ptr<Pannable> p)
        : SessionObject (s, name)
        , _pannable (p)
+       , _bypassed (false)
 {
        set_name (name);
 }
 
 PannerShell::~PannerShell ()
 {
-       DEBUG_TRACE(DEBUG::Destruction, string_compose ("panner shell for %1 destructor, pannable is %2\n", _name, _pannable));
+       DEBUG_TRACE(DEBUG::Destruction, string_compose ("panner shell %3 for %1 destructor, panner is %4, pannable is %2\n", _name, _pannable, this, _panner));
 }
 
 void
@@ -99,9 +101,9 @@ PannerShell::configure_io (ChanCount in, ChanCount out)
        }
 
        PannerInfo* pi = PannerManager::instance().select_panner (in, out);
-
-       if (pi == 0) {
-               abort ();
+       if (!pi) {
+               cerr << "No panner found: check that panners are being discovered correctly during startup.\n";
+               assert (pi);
        }
 
        boost::shared_ptr<Speakers> speakers = _session.get_speakers ();
@@ -116,7 +118,7 @@ PannerShell::configure_io (ChanCount in, ChanCount out)
        }
 
        Panner* p = pi->descriptor.factory (_pannable, speakers);
-       boost_debug_shared_ptr_mark_interesting (p, "Panner");
+       // boost_debug_shared_ptr_mark_interesting (p, "Panner");
        _panner.reset (p);
        _panner->configure_io (in, out);
 
@@ -124,18 +126,14 @@ PannerShell::configure_io (ChanCount in, ChanCount out)
 }
 
 XMLNode&
-PannerShell::get_state (void)
-{
-       return state (true);
-}
-
-XMLNode&
-PannerShell::state (bool full)
+PannerShell::get_state ()
 {
        XMLNode* node = new XMLNode ("PannerShell");
 
+       node->add_property (X_("bypassed"), _bypassed ? X_("yes") : X_("no"));
+
        if (_panner) {
-               node->add_child_nocopy (_panner->state (full));
+               node->add_child_nocopy (_panner->get_state ());
        }
 
        return *node;
@@ -149,8 +147,12 @@ PannerShell::set_state (const XMLNode& node, int version)
        const XMLProperty *prop;
        LocaleGuard lg (X_("POSIX"));
 
-       _panner.reset ();
+       if ((prop = node.property (X_("bypassed"))) != 0) {
+               set_bypassed (string_is_affirmative (prop->value ()));
+       }
 
+       _panner.reset ();
+       
        for (niter = nlist.begin(); niter != nlist.end(); ++niter) {
 
                if ((*niter)->name() == X_("Panner")) {
@@ -270,6 +272,14 @@ PannerShell::distribute_no_automation (BufferSet& inbufs, BufferSet& outbufs, pf
 void
 PannerShell::run (BufferSet& inbufs, BufferSet& outbufs, framepos_t start_frame, framepos_t end_frame, pframes_t nframes)
 {
+       if (inbufs.count().n_audio() == 0) {
+               /* Input has no audio buffers (e.g. Aux Send in a MIDI track at a
+                  point with no audio because there is no preceding instrument)
+               */
+               outbufs.silence(nframes, 0);
+               return;
+       }
+
        if (outbufs.count().n_audio() == 0) {
                // Failing to deliver audio we were asked to deliver is a bug
                assert(inbufs.count().n_audio() == 0);
@@ -326,3 +336,19 @@ PannerShell::run (BufferSet& inbufs, BufferSet& outbufs, framepos_t start_frame,
        }
 }
 
+void
+PannerShell::set_bypassed (bool yn)
+{
+       if (yn == _bypassed) {
+               return;
+       }
+       
+       _bypassed = yn;
+       Changed (); /* EMIT SIGNAL */
+}
+
+bool
+PannerShell::bypassed () const
+{
+       return _bypassed;
+}