Implement Lua session-scripts
[ardour.git] / libs / ardour / ardour / session.h
index afc93a9f76de882ae2d5421ddae44104217f3adb..d25f856b1fce7464c4eae59d81a43aa777658fa8 100644 (file)
 #include "pbd/error.h"
 #include "pbd/event_loop.h"
 #include "pbd/rcu.h"
+#include "pbd/reallocpool.h"
 #include "pbd/statefuldestructible.h"
 #include "pbd/signals.h"
 #include "pbd/undo.h"
 
+#include "lua/luastate.h"
+
 #include "evoral/types.hpp"
 
 #include "midi++/types.h"
@@ -57,6 +60,7 @@
 #include "ardour/chan_count.h"
 #include "ardour/delivery.h"
 #include "ardour/interthread_info.h"
+#include "ardour/luascripting.h"
 #include "ardour/location.h"
 #include "ardour/monitor_processor.h"
 #include "ardour/rc_configuration.h"
@@ -83,6 +87,10 @@ class Controllable;
 class ControllableDescriptor;
 }
 
+namespace luabridge {
+       class LuaRef;
+}
+
 namespace Evoral {
 class Curve;
 }
@@ -279,6 +287,7 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
        boost::shared_ptr<Route> route_by_name (std::string);
        boost::shared_ptr<Route> route_by_id (PBD::ID);
        boost::shared_ptr<Route> route_by_remote_id (uint32_t id);
+       boost::shared_ptr<Route> route_by_selected_count (uint32_t cnt);
        boost::shared_ptr<Track> track_by_diskstream_id (PBD::ID);
        void routes_using_input_from (const std::string& str, RouteList& rl);
 
@@ -305,6 +314,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
        void maybe_enable_record ();
        void disable_record (bool rt_context, bool force = false);
        void step_back_from_record ();
+       
+       void set_all_tracks_record_enabled(bool);
 
        void maybe_write_autosave ();
 
@@ -721,6 +732,13 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
 
        PBD::Signal1<void,bool> AuditionActive;
 
+       /* session script */
+       void register_lua_function (const std::string&, const std::string&, const LuaScriptParamList&);
+       void unregister_lua_function (const std::string& name);
+       std::vector<std::string> registered_lua_functions ();
+       uint32_t registered_lua_function_count () const { return _n_lua_scripts; }
+       void scripts_changed (); // called from lua, updates _n_lua_scripts
+
        /* flattening stuff */
 
        boost::shared_ptr<Region> write_one_track (Track&, framepos_t start, framepos_t end,
@@ -737,16 +755,16 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
 
        static const SessionEvent::RTeventCallback rt_cleanup;
 
-       void set_solo (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
+       void set_solo (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, PBD::Controllable::GroupControlDisposition group_override = PBD::Controllable::UseGroup);
        void clear_all_solo_state (boost::shared_ptr<RouteList>);
        void set_just_one_solo (boost::shared_ptr<Route>, bool, SessionEvent::RTeventCallback after = rt_cleanup);
-       void set_mute (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
-       void set_listen (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
-       void set_record_enabled (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
-       void set_record_safe (boost::shared_ptr<RouteList>, bool yn, 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_monitoring (boost::shared_ptr<RouteList>, MonitorChoice, SessionEvent::RTeventCallback after = rt_cleanup, bool group_override = false);
-       void set_exclusive_input_active (boost::shared_ptr<RouteList> rt, bool onoff, bool flip_others=false);
+       void set_mute (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, PBD::Controllable::GroupControlDisposition group_override = PBD::Controllable::UseGroup);
+       void set_listen (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, PBD::Controllable::GroupControlDisposition group_override = PBD::Controllable::UseGroup);
+       void set_record_enabled (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, PBD::Controllable::GroupControlDisposition group_override = PBD::Controllable::UseGroup);
+       void set_record_safe (boost::shared_ptr<RouteList>, bool yn, SessionEvent::RTeventCallback after = rt_cleanup, PBD::Controllable::GroupControlDisposition group_override = PBD::Controllable::UseGroup);
+       void set_solo_isolated (boost::shared_ptr<RouteList>, bool, SessionEvent::RTeventCallback after = rt_cleanup, PBD::Controllable::GroupControlDisposition group_override = PBD::Controllable::UseGroup);
+       void set_monitoring (boost::shared_ptr<RouteList>, MonitorChoice, SessionEvent::RTeventCallback after = rt_cleanup, PBD::Controllable::GroupControlDisposition group_override = PBD::Controllable::UseGroup);
+       void set_exclusive_input_active (boost::shared_ptr<RouteList> rt, bool onoff, bool flip_others = false);
 
        PBD::Signal1<void,bool> SoloActive;
        PBD::Signal0<void> SoloChanged;
@@ -914,6 +932,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
 
        /* Controllables */
 
+       boost::shared_ptr<Processor> processor_by_id (PBD::ID) const;
+
        boost::shared_ptr<PBD::Controllable> controllable_by_id (const PBD::ID&);
        boost::shared_ptr<PBD::Controllable> controllable_by_descriptor (const PBD::ControllableDescriptor&);
 
@@ -1269,6 +1289,21 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
        bool              pending_abort;
        bool              pending_auto_loop;
 
+       PBD::ReallocPool _mempool;
+       LuaState lua;
+       Glib::Threads::Mutex lua_lock;
+       luabridge::LuaRef * _lua_run;
+       luabridge::LuaRef * _lua_add;
+       luabridge::LuaRef * _lua_del;
+       luabridge::LuaRef * _lua_list;
+       luabridge::LuaRef * _lua_load;
+       luabridge::LuaRef * _lua_save;
+       luabridge::LuaRef * _lua_cleanup;
+       uint32_t            _n_lua_scripts;
+
+       void setup_lua ();
+       void try_run_lua (pframes_t);
+
        Butler* _butler;
 
        static const PostTransportWork ProcessCannotProceedMask =
@@ -1542,10 +1577,10 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
 
        /* mixer stuff */
 
-       void route_listen_changed (bool group_override, boost::weak_ptr<Route>);
-       void route_mute_changed (void *src);
-       void route_solo_changed (bool self_solo_change, bool group_override, boost::weak_ptr<Route>);
-       void route_solo_isolated_changed (void *src, boost::weak_ptr<Route>);
+       void route_listen_changed (PBD::Controllable::GroupControlDisposition, boost::weak_ptr<Route>);
+       void route_mute_changed ();
+       void route_solo_changed (bool self_solo_change, PBD::Controllable::GroupControlDisposition group_override, boost::weak_ptr<Route>);
+       void route_solo_isolated_changed (boost::weak_ptr<Route>);
        void update_route_solo_state (boost::shared_ptr<RouteList> r = boost::shared_ptr<RouteList>());
 
        void listen_position_changed ();
@@ -1770,8 +1805,8 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
 
        /* realtime "apply to set of routes" operations */
        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)) {
+               get_rt_event (boost::shared_ptr<RouteList> rl, T targ, SessionEvent::RTeventCallback after, PBD::Controllable::GroupControlDisposition group_override,
+                             void (Session::*method) (boost::shared_ptr<RouteList>, T, PBD::Controllable::GroupControlDisposition)) {
                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;
@@ -1780,15 +1815,15 @@ class LIBARDOUR_API Session : public PBD::StatefulDestructible, public PBD::Scop
                return ev;
        }
 
-       void rt_set_solo (boost::shared_ptr<RouteList>, bool yn, bool group_override);
-       void rt_clear_all_solo_state (boost::shared_ptr<RouteList>, bool yn, bool group_override);
-       void rt_set_just_one_solo (boost::shared_ptr<RouteList>, bool yn, bool /* ignored*/ );
-       void rt_set_mute (boost::shared_ptr<RouteList>, bool yn, bool group_override);
-       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_record_safe (boost::shared_ptr<RouteList>, bool yn, bool group_override);
-       void rt_set_monitoring (boost::shared_ptr<RouteList>, MonitorChoice, bool group_override);
+       void rt_set_solo (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition group_override);
+       void rt_clear_all_solo_state (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition group_override);
+       void rt_set_just_one_solo (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition  /* ignored*/ );
+       void rt_set_mute (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition group_override);
+       void rt_set_listen (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition group_override);
+       void rt_set_solo_isolated (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition group_override);
+       void rt_set_record_enabled (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition group_override);
+       void rt_set_record_safe (boost::shared_ptr<RouteList>, bool yn, PBD::Controllable::GroupControlDisposition group_override);
+       void rt_set_monitoring (boost::shared_ptr<RouteList>, MonitorChoice, PBD::Controllable::GroupControlDisposition group_override);
 
        /** temporary list of Diskstreams used only during load of 2.X sessions */
        std::list<boost::shared_ptr<Diskstream> > _diskstreams_2X;