1 // Boost.Signals library
3 // Copyright Douglas Gregor 2001-2004. Use, modification and
4 // distribution is subject to the Boost Software License, Version
5 // 1.0. (See accompanying file LICENSE_1_0.txt or copy at
6 // http://www.boost.org/LICENSE_1_0.txt)
8 // For more information, see http://www.boost.org
10 #ifndef BOOST_SIGNALS_SLOT_HEADER
11 #define BOOST_SIGNALS_SLOT_HEADER
13 #include <boost/signals/detail/signals_common.hpp>
14 #include <boost/signals/connection.hpp>
15 #include <boost/signals/trackable.hpp>
16 #include <boost/visit_each.hpp>
17 #include <boost/shared_ptr.hpp>
20 #ifdef BOOST_HAS_ABI_HEADERS
21 # include BOOST_ABI_PREFIX
25 namespace BOOST_SIGNALS_NAMESPACE
{
27 class BOOST_SIGNALS_DECL slot_base
{
28 // We would have to enumerate all of the signalN classes here as
29 // friends to make this private (as it otherwise should be). We can't
30 // name all of them because we don't know how many there are.
33 std::vector
<const trackable
*> bound_objects
;
34 connection watch_bound_objects
;
36 shared_ptr
<data_t
> get_data() const { return data
; }
38 // Get the set of bound objects
39 std::vector
<const trackable
*>& get_bound_objects() const
40 { return data
->bound_objects
; }
42 // Determine if this slot is still "active", i.e., all of the bound
43 // objects still exist
44 bool is_active() const
45 { return data
->watch_bound_objects
.connected(); }
48 // Create a connection for this slot
49 void create_connection();
51 shared_ptr
<data_t
> data
;
54 static void bound_object_destructed(void*, void*) {}
56 } // end namespace detail
58 // Get the slot so that it can be copied
60 reference_wrapper
<const F
>
61 get_invocable_slot(const F
& f
, BOOST_SIGNALS_NAMESPACE::detail::signal_tag
)
62 { return reference_wrapper
<const F
>(f
); }
66 get_invocable_slot(const F
& f
, BOOST_SIGNALS_NAMESPACE::detail::reference_tag
)
71 get_invocable_slot(const F
& f
, BOOST_SIGNALS_NAMESPACE::detail::value_tag
)
74 // Get the slot so that it can be inspected for trackable objects
77 get_inspectable_slot(const F
& f
, BOOST_SIGNALS_NAMESPACE::detail::signal_tag
)
82 get_inspectable_slot(const reference_wrapper
<F
>& f
, BOOST_SIGNALS_NAMESPACE::detail::reference_tag
)
87 get_inspectable_slot(const F
& f
, BOOST_SIGNALS_NAMESPACE::detail::value_tag
)
90 // Determines the type of the slot - is it a signal, a reference to a
91 // slot or just a normal slot.
93 typename
BOOST_SIGNALS_NAMESPACE::detail::get_slot_tag
<F
>::type
96 typedef typename
BOOST_SIGNALS_NAMESPACE::detail::get_slot_tag
<F
>::type
98 the_tag_type tag
= the_tag_type();
102 } // end namespace BOOST_SIGNALS_NAMESPACE
104 template<typename SlotFunction
>
105 class slot
: public BOOST_SIGNALS_NAMESPACE::detail::slot_base
{
106 typedef BOOST_SIGNALS_NAMESPACE::detail::slot_base inherited
;
107 typedef typename
inherited::data_t data_t
;
111 slot(const F
& f
) : slot_function(BOOST_SIGNALS_NAMESPACE::get_invocable_slot(f
, BOOST_SIGNALS_NAMESPACE::tag_type(f
)))
113 this->data
.reset(new data_t
);
115 // Visit each of the bound objects and store them for later use
116 // An exception thrown here will allow the basic_connection to be
117 // destroyed when this goes out of scope, and no other connections
119 BOOST_SIGNALS_NAMESPACE::detail::bound_objects_visitor
120 do_bind(this->data
->bound_objects
);
122 BOOST_SIGNALS_NAMESPACE::get_inspectable_slot
123 (f
, BOOST_SIGNALS_NAMESPACE::tag_type(f
)));
129 slot(F
* f
) : slot_function(f
)
131 this->data
.reset(new data_t
);
134 #endif // __BORLANDC__
136 // We would have to enumerate all of the signalN classes here as friends
137 // to make this private (as it otherwise should be). We can't name all of
138 // them because we don't know how many there are.
140 // Get the slot function to call the actual slot
141 const SlotFunction
& get_slot_function() const { return slot_function
; }
143 void release() const { data
->watch_bound_objects
.set_controlling(false); }
146 slot(); // no default constructor
147 slot
& operator=(const slot
&); // no assignment operator
149 SlotFunction slot_function
;
151 } // end namespace boost
153 #ifdef BOOST_HAS_ABI_HEADERS
154 # include BOOST_ABI_SUFFIX
157 #endif // BOOST_SIGNALS_SLOT_HEADER