summaryrefslogtreecommitdiff
path: root/libs/pbd
diff options
context:
space:
mode:
Diffstat (limited to 'libs/pbd')
-rw-r--r--libs/pbd/base_ui.cc2
-rw-r--r--libs/pbd/controllable.cc2
-rw-r--r--libs/pbd/event_loop.cc19
-rw-r--r--libs/pbd/pbd/base_ui.h4
-rw-r--r--libs/pbd/pbd/event_loop.h (renamed from libs/pbd/pbd/ui_callback.h)18
-rw-r--r--libs/pbd/pbd/memento_command.h2
-rw-r--r--libs/pbd/pbd/shiva.h139
-rw-r--r--libs/pbd/pbd/signals.h98
-rw-r--r--libs/pbd/ui_callback.cc19
-rw-r--r--libs/pbd/undo.cc4
-rw-r--r--libs/pbd/wscript2
11 files changed, 116 insertions, 193 deletions
diff --git a/libs/pbd/base_ui.cc b/libs/pbd/base_ui.cc
index ea7e469c74..5e856d1ca0 100644
--- a/libs/pbd/base_ui.cc
+++ b/libs/pbd/base_ui.cc
@@ -70,7 +70,7 @@ BaseUI::new_request_type ()
void
BaseUI::main_thread ()
{
- set_ui_for_thread (this);
+ set_event_loop_for_thread (this);
thread_init ();
_main_loop->run ();
}
diff --git a/libs/pbd/controllable.cc b/libs/pbd/controllable.cc
index dd0dfd4445..d751c3c80b 100644
--- a/libs/pbd/controllable.cc
+++ b/libs/pbd/controllable.cc
@@ -62,7 +62,7 @@ Controllable::add (Controllable& ctl)
/* Controllable::remove() is static - no need to manage this connection */
- ctl.GoingAway.connect (registry_connections, boost::bind (&Controllable::remove, ref (ctl)));
+ ctl.GoingAway.connect_same_thread (registry_connections, boost::bind (&Controllable::remove, ref (ctl)));
}
void
diff --git a/libs/pbd/event_loop.cc b/libs/pbd/event_loop.cc
new file mode 100644
index 0000000000..3bc4abcbdf
--- /dev/null
+++ b/libs/pbd/event_loop.cc
@@ -0,0 +1,19 @@
+#include "pbd/event_loop.h"
+
+using namespace PBD;
+
+Glib::StaticPrivate<EventLoop> EventLoop::thread_event_loop;
+
+static void do_not_delete_the_loop_pointer (void*) { }
+
+EventLoop*
+EventLoop::get_event_loop_for_thread() {
+ return thread_event_loop.get ();
+}
+
+void
+EventLoop::set_event_loop_for_thread (EventLoop* loop)
+{
+ thread_event_loop.set (loop, do_not_delete_the_loop_pointer);
+}
+
diff --git a/libs/pbd/pbd/base_ui.h b/libs/pbd/pbd/base_ui.h
index 2bfaa11be0..9e88be60f2 100644
--- a/libs/pbd/pbd/base_ui.h
+++ b/libs/pbd/pbd/base_ui.h
@@ -30,9 +30,9 @@
#include <glibmm/main.h>
#include "pbd/crossthread.h"
-#include "pbd/ui_callback.h"
+#include "pbd/event_loop.h"
-class BaseUI : virtual public sigc::trackable, public PBD::UICallback
+class BaseUI : virtual public sigc::trackable, public PBD::EventLoop
{
public:
BaseUI (const std::string& name);
diff --git a/libs/pbd/pbd/ui_callback.h b/libs/pbd/pbd/event_loop.h
index 8574de0dec..be98fcd852 100644
--- a/libs/pbd/pbd/ui_callback.h
+++ b/libs/pbd/pbd/event_loop.h
@@ -17,8 +17,8 @@
*/
-#ifndef __pbd_ui_callback_h__
-#define __pbd_ui_callback_h__
+#ifndef __pbd_event_loop_h__
+#define __pbd_event_loop_h__
#include <boost/function.hpp>
#include <boost/bind.hpp> /* we don't need this here, but anything calling call_slot() probably will, so this is convenient */
@@ -27,22 +27,22 @@
namespace PBD
{
-class UICallback
+class EventLoop
{
public:
- UICallback() {}
- virtual ~UICallback() {}
+ EventLoop() {}
+ virtual ~EventLoop() {}
virtual void call_slot (const boost::function<void()>&) = 0;
- static UICallback* get_ui_for_thread();
- static void set_ui_for_thread (UICallback* ui);
+ static EventLoop* get_event_loop_for_thread();
+ static void set_event_loop_for_thread (EventLoop* ui);
private:
- static Glib::StaticPrivate<UICallback> thread_ui;
+ static Glib::StaticPrivate<EventLoop> thread_event_loop;
};
}
-#endif /* __pbd_ui_callback_h__ */
+#endif /* __pbd_event_loop_h__ */
diff --git a/libs/pbd/pbd/memento_command.h b/libs/pbd/pbd/memento_command.h
index b87f784334..a08d3bb717 100644
--- a/libs/pbd/pbd/memento_command.h
+++ b/libs/pbd/pbd/memento_command.h
@@ -42,7 +42,7 @@ public:
: obj(a_object), before(a_before), after(a_after)
{
/* if the object dies, make sure that we die and that everyone knows about it */
- obj.GoingAway.connect (obj_death_connection, boost::bind (&MementoCommand::object_died, this));
+ obj.GoingAway.connect_same_thread (obj_death_connection, boost::bind (&MementoCommand::object_died, this));
}
~MementoCommand () {
diff --git a/libs/pbd/pbd/shiva.h b/libs/pbd/pbd/shiva.h
deleted file mode 100644
index 90adad6250..0000000000
--- a/libs/pbd/pbd/shiva.h
+++ /dev/null
@@ -1,139 +0,0 @@
-/*
- Copyright (C) 2000-2007 Paul Davis
-
- This program is free software; you can redistribute it and/or modify
- it under the terms of the GNU General Public License as published by
- the Free Software Foundation; either version 2 of the License, or
- (at your option) any later version.
-
- This program is distributed in the hope that it will be useful,
- but WITHOUT ANY WARRANTY; without even the implied warranty of
- MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
- GNU General Public License for more details.
-
- You should have received a copy of the GNU General Public License
- along with this program; if not, write to the Free Software
- Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
-
-*/
-
-#ifndef __pbd_shiva_h__
-#define __pbd_shiva_h__
-
-#include <sigc++/sigc++.h>
-
-namespace PBD {
-
-/* named after the Hindu god Shiva, The Destroyer */
-
-template<typename ObjectWithGoingAway, typename ObjectToBeDestroyed>
-class Shiva : public sigc::trackable
-{
- public:
- Shiva (ObjectWithGoingAway& emitter, ObjectToBeDestroyed& receiver) {
-
- /* if the emitter goes away, destroy the receiver */
-
- _connection = emitter.GoingAway.connect
- (sigc::bind (sigc::mem_fun
- (*this, &Shiva<ObjectWithGoingAway,ObjectToBeDestroyed>::destroy),
- &receiver));
- }
-
- ~Shiva() {
- forget ();
- }
-
- private:
- sigc::connection _connection;
-
- void destroy (ObjectToBeDestroyed* obj) {
- delete obj;
- forget ();
- }
-
- void forget () {
- _connection.disconnect ();
- }
-
-};
-
-template<typename ObjectWithGoingAway, typename ObjectToBeDestroyed>
-class ProxyShiva : public sigc::trackable
-{
- public:
- ProxyShiva (ObjectWithGoingAway& emitter, ObjectToBeDestroyed& receiver, void (*callback)(ObjectToBeDestroyed*, ObjectWithGoingAway*)) {
-
- /* if the emitter goes away, destroy the receiver */
-
- _callback = callback;
- _callback_argument = &emitter;
-
- _connection = emitter.GoingAway.connect
- (sigc::bind (sigc::mem_fun
- (*this, &ProxyShiva<ObjectWithGoingAway,ObjectToBeDestroyed>::destroy),
- &receiver));
- }
-
- ~ProxyShiva () {
- forget ();
- }
-
- private:
- sigc::connection _connection;
- void (*_callback) (ObjectToBeDestroyed*, ObjectWithGoingAway*);
- ObjectWithGoingAway* _callback_argument;
-
- void destroy (ObjectToBeDestroyed* obj) {
- /* callback must destroy obj if appropriate, not done here */
- _callback (obj, _callback_argument);
- forget ();
- }
-
- void forget () {
- _connection.disconnect ();
- }
-};
-
-template<typename ObjectWithGoingAway, typename ObjectToBeDestroyed>
-class PairedShiva : public sigc::trackable
-{
- public:
- PairedShiva (ObjectWithGoingAway& emitter, ObjectToBeDestroyed& receiver) {
-
- /* if the emitter goes away, destroy the receiver */
-
- _connection1 = emitter.GoingAway.connect
- (sigc::bind (sigc::mem_fun
- (*this, &PairedShiva<ObjectWithGoingAway,ObjectToBeDestroyed>::destroy),
- &receiver));
-
- /* if the receiver goes away, forget all this nonsense */
-
- _connection2 = receiver.GoingAway.connect
- (sigc::mem_fun (*this, &PairedShiva<ObjectWithGoingAway,ObjectToBeDestroyed>::forget));
- }
-
- ~PairedShiva() {
- forget ();
- }
-
- private:
- sigc::connection _connection1;
- sigc::connection _connection2;
-
- void destroy (ObjectToBeDestroyed* obj) {
- delete obj;
- forget ();
- }
-
- void forget () {
- _connection1.disconnect ();
- _connection2.disconnect ();
- }
-
-};
-
-}
-
-#endif /* __pbd_shiva_h__ */
diff --git a/libs/pbd/pbd/signals.h b/libs/pbd/pbd/signals.h
index 47e8d143bc..0b44ee8051 100644
--- a/libs/pbd/pbd/signals.h
+++ b/libs/pbd/pbd/signals.h
@@ -22,8 +22,13 @@
#include <list>
#include <glibmm/thread.h>
+
#include <boost/signals2.hpp>
#include <boost/noncopyable.hpp>
+#include <boost/bind.hpp>
+#include <boost/bind/protect.hpp>
+
+#include "pbd/event_loop.h"
namespace PBD {
@@ -40,10 +45,6 @@ class ScopedConnectionList : public boost::noncopyable
void add_connection (const UnscopedConnection& c);
void drop_connections ();
- template<typename S> void scoped_connect (S& sig, const typename S::slot_function_type& sf) {
- add_connection (sig.connect (sf));
- }
-
private:
/* this class is not copyable */
ScopedConnectionList(const ScopedConnectionList&);
@@ -76,14 +77,26 @@ public:
Signal0 () {}
typedef boost::signals2::signal<R()> SignalType;
- void connect (ScopedConnectionList& clist,
+ void connect_same_thread (Connection& c,
+ const typename SignalType::slot_function_type& slot) {
+ c = _signal.connect (slot);
+ }
+
+ void connect_same_thread (ScopedConnectionList& clist,
const typename SignalType::slot_function_type& slot) {
clist.add_connection (_signal.connect (slot));
}
+
+ void connect (ScopedConnectionList& clist,
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ clist.add_connection (_signal.connect (boost::bind (&EventLoop::call_slot, event_loop, slot)));
+ }
void connect (Connection& c,
- const typename SignalType::slot_function_type& slot) {
- c = _signal.connect (slot);
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ c = _signal.connect (boost::bind (&EventLoop::call_slot, event_loop, slot));
}
typename SignalType::result_type operator()() {
@@ -100,15 +113,32 @@ public:
Signal1 () {}
typedef boost::signals2::signal<R(A)> SignalType;
- void connect (ScopedConnectionList& clist,
+ void connect_same_thread (ScopedConnectionList& clist,
const typename SignalType::slot_function_type& slot) {
clist.add_connection (_signal.connect (slot));
}
- void connect (Connection& c,
- const typename SignalType::slot_function_type& slot) {
+ void connect_same_thread (Connection& c,
+ const typename SignalType::slot_function_type& slot) {
c = _signal.connect (slot);
}
+
+ static void compositor (typename boost::function<void(A)> f, EventLoop* event_loop, A arg) {
+ event_loop->call_slot (boost::bind (f, arg));
+ }
+
+ void connect (ScopedConnectionList& clist,
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ clist.add_connection (_signal.connect (boost::bind (&compositor, slot, event_loop, _1)));
+ }
+
+ void connect (Connection& c,
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ c = _signal.connect (boost::bind (&compositor, slot, event_loop, _1));
+
+ }
typename SignalType::result_type operator()(A arg1) {
return _signal (arg1);
@@ -124,16 +154,32 @@ public:
Signal2 () {}
typedef boost::signals2::signal<R(A1, A2)> SignalType;
- void connect (ScopedConnectionList& clist,
+ void connect_same_thread (ScopedConnectionList& clist,
const typename SignalType::slot_function_type& slot) {
clist.add_connection (_signal.connect (slot));
}
-
- void connect (Connection& c,
- const typename SignalType::slot_function_type& slot) {
+
+ void connect_same_thread (Connection& c,
+ const typename SignalType::slot_function_type& slot) {
c = _signal.connect (slot);
}
-
+
+ static void compositor (typename boost::function<void(A1,A2)> f, PBD::EventLoop* event_loop, A1 arg1, A2 arg2) {
+ event_loop->call_slot (boost::bind (f, arg1, arg2));
+ }
+
+ void connect (ScopedConnectionList& clist,
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ clist.add_connection (_signal.connect (boost::bind (&compositor, slot, event_loop, _1, _2)));
+ }
+
+ void connect (Connection& c,
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ c = _signal.connect (boost::bind (&compositor, slot, event_loop, _1, _2));
+ }
+
typename SignalType::result_type operator()(A1 arg1, A2 arg2) {
return _signal (arg1, arg2);
}
@@ -148,14 +194,30 @@ public:
Signal3 () {}
typedef boost::signals2::signal<R(A1,A2,A3)> SignalType;
- void connect (ScopedConnectionList& clist,
+ void connect_same_thread (ScopedConnectionList& clist,
const typename SignalType::slot_function_type& slot) {
clist.add_connection (_signal.connect (slot));
}
+
+ void connect_same_thread (Connection& c,
+ const typename SignalType::slot_function_type& slot) {
+ c = _signal.connect (slot);
+ }
+
+ static void compositor (typename boost::function<void(A1,A2,A3)> f, PBD::EventLoop* event_loop, A1 arg1, A2 arg2, A3 arg3) {
+ event_loop->call_slot (boost::bind (f, arg1, arg2, arg3));
+ }
+
+ void connect (ScopedConnectionList& clist,
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ clist.add_connection (_signal.connect (boost::bind (&compositor, slot, event_loop, _1, _2, _3)));
+ }
void connect (Connection& c,
- const typename SignalType::slot_function_type& slot) {
- c = _signal.connect (slot);
+ const typename SignalType::slot_function_type& slot,
+ PBD::EventLoop* event_loop) {
+ c = _signal.connect (_signal.connect (boost::bind (&compositor, slot, event_loop, _1, _2, _3)));
}
typename SignalType::result_type operator()(A1 arg1, A2 arg2, A3 arg3) {
diff --git a/libs/pbd/ui_callback.cc b/libs/pbd/ui_callback.cc
deleted file mode 100644
index 9a8feb3d2c..0000000000
--- a/libs/pbd/ui_callback.cc
+++ /dev/null
@@ -1,19 +0,0 @@
-#include "pbd/ui_callback.h"
-
-using namespace PBD;
-
-Glib::StaticPrivate<UICallback> UICallback::thread_ui;
-
-static void do_not_delete_the_ui_pointer (void*) { }
-
-UICallback*
-UICallback::get_ui_for_thread() {
- return thread_ui.get ();
-}
-
-void
-UICallback::set_ui_for_thread (UICallback* ui)
-{
- thread_ui.set (ui, do_not_delete_the_ui_pointer);
-}
-
diff --git a/libs/pbd/undo.cc b/libs/pbd/undo.cc
index 1a2574ae28..81e31f3a88 100644
--- a/libs/pbd/undo.cc
+++ b/libs/pbd/undo.cc
@@ -83,7 +83,7 @@ UndoTransaction::add_command (Command *const action)
so there is no need to manage this connection.
*/
- action->GoingAway.connect (*this, boost::bind (&command_death, this, action));
+ action->GoingAway.connect_same_thread (*this, boost::bind (&command_death, this, action));
actions.push_back (action);
}
@@ -186,7 +186,7 @@ UndoHistory::add (UndoTransaction* const ut)
{
uint32_t current_depth = UndoList.size();
- ut->GoingAway.connect (*this, boost::bind (&UndoHistory::remove, this, ut));
+ ut->GoingAway.connect_same_thread (*this, boost::bind (&UndoHistory::remove, this, ut));
/* if the current undo history is larger than or equal to the currently
requested depth, then pop off at least 1 element to make space
diff --git a/libs/pbd/wscript b/libs/pbd/wscript
index d7e456ada7..b25d8059ce 100644
--- a/libs/pbd/wscript
+++ b/libs/pbd/wscript
@@ -59,6 +59,7 @@ def build(bld):
controllable.cc
crossthread.cc
enumwriter.cc
+ event_loop.cc
dmalloc.cc
error.cc
filesystem.cc
@@ -82,7 +83,6 @@ def build(bld):
strsplit.cc
textreceiver.cc
transmitter.cc
- ui_callback.cc
undo.cc
uuid.cc
version.cc