connection_handler.h

Go to the documentation of this file.
00001 #ifndef _SIGX_CONNECTION_HANDLER_HPP_
00002 #define _SIGX_CONNECTION_HANDLER_HPP_
00003 
00004 /*
00005  * Copyright 2005 Klaus Triendl
00006  *
00007  * This library is free software; you can redistribute it and/or
00008  * modify it under the terms of the GNU Library General Public
00009  * License as published by the Free Software Foundation; either
00010  * version 2 of the License, or (at your option) any later version.
00011  *
00012  * This library is distributed in the hope that it will be useful,
00013  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00014  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00015  * Library General Public License for more details.
00016  *
00017  * You should have received a copy of the GNU Library General Public
00018  * License along with this library; if not, write to the Free 
00019  * Software Foundation, 51 Franklin Street, Fifth Floor, 
00020  * Boston, MA 02110-1301, USA.
00021  */
00022 
00023 #include <tr1/memory>   // std::tr1::shared_ptr
00024 #include <map>
00025 #include <sigc++/signal.h>
00026 #include <glib.h>   // message macros
00027 #include <glibmm/thread.h> // Glib::StaticPrivate
00028 #include <glibmm/main.h>
00029 #include <sigxconfig.h>
00030 #include <sigx/fwddecl.h>
00031 #include <sigx/noninstantiatable.h>
00032 #include <sigx/signal_traits.h>
00033 #include <sigx/signal_source_base.h>
00034 #include <sigx/connection_wrapper.h>
00035 
00036 
00037 namespace sigx
00038 {
00039 
00044 class SIGX_API connection_handler: noninstantiatable
00045 {
00046 public:
00054     static void destroy(const sigc_connection_ptr* handle);
00055 
00060     static void store(
00061         const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconn, 
00062         const sigc::connection& c);
00063 
00064 
00065 protected:
00074     struct connections_container_wrapper
00075     {
00080 #if 1
00081         typedef std::map<const sigc_connection_ptr* const /*handle*/, std::tr1::shared_ptr<sigc_connection_ptr> > container_type;
00082 #else
00083         typedef std::map<const void* const /*handle*/, sigc::connection*> container_type;
00084 #endif
00085 
00086         container_type m_connections;
00087         ~connections_container_wrapper();
00088     };
00089 
00090     static Glib::StaticPrivate<connections_container_wrapper> thread_specific_connections;
00091 };
00092 
00093 
00094 template<typename T_signal, internal::signal_group I_oneof>
00095 class typed_connection_handler;
00096 
00097 template<typename T_signal>
00098 class typed_connection_handler<T_signal, internal::SIGGROUP_SIGC>: noninstantiatable
00099 {
00100 public:
00101     typedef T_signal signal_type;
00102     typedef typename signal_type::slot_type slot_type;
00103 
00108     static void connect(const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconnptr, const std::tr1::shared_ptr<signal_source_base>& psigsource, const slot_type& _A_slot)
00109     {
00110         // must have a valid signal source
00111         g_return_if_fail(psigsource.get());
00112 
00113         // get the signal from the signal source ...
00114         typedef signal_type (*fp_sig_getter)(signal_source_ptr);
00115         const fp_sig_getter getsig = 
00116             reinterpret_cast<fp_sig_getter>(psigsource->getter());
00117 
00118         // ... and connect the slot
00119         const sigc::connection& c = getsig(psigsource.get()).connect(_A_slot);
00120         // ... store the resulting connection in the container of the thread's connections
00121         connection_handler::store(_A_refconnptr, c);
00122     }
00123 };
00124 
00127 template<typename T_signal>
00128 class typed_connection_handler<T_signal, internal::SIGGROUP_GLIB_PROXY>: noninstantiatable
00129 {
00130 public:
00131     typedef T_signal signal_type;
00132     typedef typename signal_type::SlotType slot_type;
00133     typedef typename signal_type::VoidSlotType void_slot_type;
00134 
00137     static void connect(const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconnptr, const std::tr1::shared_ptr<signal_source_base>& psigsource, const slot_type& _A_slot, bool after)
00138     {
00139         // must have a valid signal source
00140         g_return_if_fail(psigsource.get());
00141 
00142         // get the signal from the signal source ...
00143         typedef signal_type (*fp_sig_getter)(signal_source_ptr);
00144         const fp_sig_getter getsig = 
00145             reinterpret_cast<fp_sig_getter>(psigsource->getter());
00146 
00147         // ... and connect the slot
00148         const sigc::connection& c = getsig(psigsource.get()).connect(_A_slot, after);
00149         // ... store the resulting connection in the container of the thread's connections
00150         connection_handler::store(_A_refconnptr, c);
00151     }
00152 
00155     static void connect_notify(const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconnptr, const std::tr1::shared_ptr<signal_source_base>& psigsource, const void_slot_type& _A_slot, bool after)
00156     {
00157         // must have a valid signal source
00158         g_return_if_fail(psigsource.get());
00159 
00160         // get the signal from the signal source ...
00161         typedef signal_type (*fp_sig_getter)(signal_source_ptr);
00162         const fp_sig_getter getsig = 
00163             reinterpret_cast<fp_sig_getter>(psigsource->getter());
00164 
00165         // ... and connect the slot
00166         const sigc::connection& c = getsig(psigsource.get()).connect_notify(_A_slot, after);
00167         // ... store the resulting connection in the container of the thread's connections
00168         connection_handler::store(_A_refconnptr, c);
00169     }
00170 };
00171 
00174 template<>
00175 class SIGX_API typed_connection_handler<Glib::SignalIdle, internal::SIGGROUP_IRRELEVANT>: noninstantiatable
00176 {
00177 public:
00178     typedef Glib::SignalIdle signal_type;
00179     typedef sigc::slot<bool> slot_type;
00180 
00183     static void connect(const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconnptr, const std::tr1::shared_ptr<signal_source_base>& psigsource, const slot_type& _A_slot, int priority);
00184 };
00185 
00186 
00189 template<>
00190 class SIGX_API typed_connection_handler<Glib::SignalTimeout, internal::SIGGROUP_IRRELEVANT>: noninstantiatable
00191 {
00192 public:
00193     typedef Glib::SignalTimeout signal_type;
00194     typedef sigc::slot<bool> slot_type;
00195 
00198     static void connect(const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconnptr, const std::tr1::shared_ptr<signal_source_base>& psigsource, const slot_type& _A_slot, unsigned int interval, int priority);
00199 };
00200 
00201 
00204 template<>
00205 class SIGX_API typed_connection_handler<Glib::SignalIO, internal::SIGGROUP_IRRELEVANT>: noninstantiatable
00206 {
00207 public:
00208     typedef Glib::SignalIO signal_type;
00209     typedef sigc::slot<bool, Glib::IOCondition> slot_type;
00210 
00213     static void connect(const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconnptr, const std::tr1::shared_ptr<signal_source_base>& psigsource, const slot_type& _A_slot, int fd, Glib::IOCondition condition, int priority);
00214 };
00215 
00216 
00219 template<>
00220 class SIGX_API typed_connection_handler<Glib::SignalChildWatch, internal::SIGGROUP_IRRELEVANT>: noninstantiatable
00221 {
00222 public:
00223     typedef Glib::SignalChildWatch signal_type;
00224     typedef sigc::slot<void, GPid, int> slot_type;
00225 
00228     static void connect(const std::tr1::shared_ptr<sigc_connection_ptr>& _A_refconnptr, const std::tr1::shared_ptr<signal_source_base>& psigsource, const slot_type& _A_slot, GPid pid, int priority);
00229 };
00230 
00231 
00232 } // namespace sigx
00233 
00234 
00235 #endif // end file guard

Generated on Wed Jan 28 21:37:59 2009 for sigx++ by  doxygen 1.5.8