diff --git a/Makefile.am b/Makefile.am
index db7fa4cb..9a28af1f 100644
--- a/Makefile.am
+++ b/Makefile.am
@@ -118,6 +118,7 @@ UTIL_FILES = \
si.cpp \
signal.cpp \
signal.hpp \
+ signal.ipp \
si.hpp \
stats.cpp \
stats.hpp \
diff --git a/signal.hpp b/signal.hpp
index e4deb16b..f25355fc 100644
--- a/signal.hpp
+++ b/signal.hpp
@@ -14,11 +14,11 @@
* You should have received a copy of the GNU General Public License
* along with libgim. If not, see .
*
- * Copyright 2011 Danny Robson
+ * Copyright 2011-2013 Danny Robson
*/
-#ifndef __SIGNAL_HPP
-#define __SIGNAL_HPP
+#ifndef __UTIL_SIGNAL_HPP
+#define __UTIL_SIGNAL_HPP
#include "debug.hpp"
#include "nocopy.hpp"
@@ -44,83 +44,34 @@ namespace util {
cookie m_cookie;
signal& m_parent;
- scoped_cookie (cookie _cookie,
- signal &_parent):
- m_cookie (_cookie),
- m_parent (_parent)
- { ; }
+ scoped_cookie (cookie _cookie, signal &_parent);
+ scoped_cookie (scoped_cookie &&rhs);
+ ~scoped_cookie ();
- scoped_cookie (scoped_cookie &&rhs):
- m_cookie (rhs.m_cookie),
- m_parent (rhs.m_parent)
- {
- rhs.m_cookie = rhs.m_parent.m_children.end ();
- }
-
- ~scoped_cookie () {
- if (m_parent.m_children.end () != m_cookie)
- m_parent.disconnect (m_cookie);
- }
-
- void renew (callback_object &&cb)
- { *m_cookie = std::move (cb); }
-
- void release (void)
- { m_cookie = m_parent.m_children.end (); }
+ void renew (callback_object &&cb);
+ void release (void);
};
public:
- signal ()
- { /*m_children.reserve (16);*/ }
-
+ signal ();
/// Add a callback to list.
- const cookie
- connect (const callback_object &_cb)
- { return m_children.insert (m_children.end (), _cb); }
-
-
- /// Add a callback to the list.
- //const cookie
- //connect (const callback_function &_cb)
- // { return m_children.insert (m_children.end (), _cb); }
-
-
- void disconnect (const cookie _cb)
- { m_children.erase (_cb); }
-
+ cookie connect (const callback_object &_cb);
+ scoped_cookie scoped_connect (const callback_object &_cb);
+ void disconnect (const cookie _cb);
/// Disconnect all callbacks
- void clear (void)
- { m_children.clear (); }
-
+ void clear (void);
/// Returns the number of callbacks connected.
- unsigned int size (void) const
- { return m_children.size (); }
-
-
- bool empty (void) const
- { return m_children.empty (); }
-
+ unsigned int size (void) const;
+ bool empty (void) const;
/// Execute all callbacks, ignoring the return parameters. Does not combine results.
- void operator () (Args... tail) {
- if (m_children.empty ())
- return;
-
- auto i = m_children.cbegin ();
- bool looping;
-
- do {
- // Increment before we execute so that the caller is able to deregister during execution.
- auto current = i++;
- looping = m_children.cend () != i;
-
- (*current)(tail...);
- } while (looping);
- }
+ void operator () (Args... tail);
};
}
+#include "signal.ipp"
+
#endif // __SIGNAL_HPP
diff --git a/signal.ipp b/signal.ipp
new file mode 100644
index 00000000..d1d701b2
--- /dev/null
+++ b/signal.ipp
@@ -0,0 +1,128 @@
+/*
+ * This file is part of libgim.
+ *
+ * libgim 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 3 of the License, or (at your option) any later
+ * version.
+ *
+ * libgim 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 libgim. If not, see .
+ *
+ * Copyright 2011-2013 Danny Robson
+ */
+
+#ifndef __UTIL_SIGNAL_HPP
+#error
+#endif
+
+namespace util {
+ template
+ signal::scoped_cookie::scoped_cookie (cookie _cookie,
+ signal &_parent):
+ m_cookie (_cookie),
+ m_parent (_parent)
+ { ; }
+
+
+ template
+ signal::scoped_cookie::scoped_cookie (scoped_cookie &&rhs):
+ m_cookie (rhs.m_cookie),
+ m_parent (rhs.m_parent)
+ {
+ rhs.m_cookie = rhs.m_parent.m_children.end ();
+ }
+
+
+ template
+ signal::scoped_cookie::~scoped_cookie () {
+ if (m_parent.m_children.end () != m_cookie)
+ m_parent.disconnect (m_cookie);
+ }
+
+
+ template
+ void
+ signal::scoped_cookie::renew (callback_object &&cb)
+ { *m_cookie = std::move (cb); }
+
+
+ template
+ void
+ signal::scoped_cookie::release (void)
+ { m_cookie = m_parent.m_children.end (); }
+
+
+ template
+ signal::signal ()
+ { ; }
+
+
+ template
+ typename signal::cookie
+ signal::connect (const callback_object &_cb)
+ { return m_children.insert (m_children.end (), _cb); }
+
+
+ template
+ typename signal::scoped_cookie
+ signal::scoped_connect (const callback_object &_cb)
+ { return scoped_cookie (connect (_cb), *this); }
+
+
+ /// Add a callback to the list.
+ //const cookie
+ //connect (const callback_function &_cb)
+ // { return m_children.insert (m_children.end (), _cb); }
+
+
+ template
+ void
+ signal::disconnect (const cookie _cb)
+ { m_children.erase (_cb); }
+
+
+ /// Disconnect all callbacks
+ template
+ void
+ signal::clear (void)
+ { m_children.clear (); }
+
+
+ /// Returns the number of callbacks connected.
+ template
+ unsigned int
+ signal::size (void) const
+ { return m_children.size (); }
+
+
+ template
+ bool
+ signal::empty (void) const
+ { return m_children.empty (); }
+
+
+ template
+ void
+ signal::operator () (Args... tail) {
+ if (m_children.empty ())
+ return;
+
+ auto i = m_children.cbegin ();
+ bool looping;
+
+ do {
+ // Increment before we execute so that the caller is able to deregister during execution.
+ auto current = i++;
+ looping = m_children.cend () != i;
+
+ (*current)(tail...);
+ } while (looping);
+ }
+}
+