1919
2020#include " aligned_storage.hpp"
2121#include " macros.hpp"
22+ #include " ref_counted.hpp"
2223
2324#include < new>
2425#include < stddef.h>
@@ -41,6 +42,14 @@ class Callback {
4142 STATIC_ASSERT (ALIGN_OF (Storage) >= ALIGN_OF (MemberInvoker));
4243 }
4344
45+ template <class F , class T >
46+ Callback (F func, SharedRefPtr<T> ptr)
47+ : invoker_(new (&storage_) MemberPtrInvoker<F, T>(func, ptr)) {
48+ typedef MemberInvoker<F, T> MemberPtrInvoker;
49+ STATIC_ASSERT (sizeof (Storage) >= sizeof (MemberPtrInvoker));
50+ STATIC_ASSERT (ALIGN_OF (Storage) >= ALIGN_OF (MemberPtrInvoker));
51+ }
52+
4453 template <class F >
4554 explicit Callback (F func)
4655 : invoker_(new (&storage_) FunctionInvoker<F>(func)) {
@@ -96,6 +105,20 @@ class Callback {
96105 T* object;
97106 };
98107
108+ template <class F , class T >
109+ struct MemberPtrInvoker : public Invoker {
110+ MemberPtrInvoker (F func, const SharedRefPtr<T>& ptr)
111+ : func(func)
112+ , ptr(ptr) {}
113+
114+ R invoke (const Arg& arg) const { return (ptr.get ()->*func)(arg); }
115+
116+ Invoker* copy (Storage* storage) { return new (storage) MemberPtrInvoker<F, T>(func, ptr); }
117+
118+ F func;
119+ SharedRefPtr<T> ptr;
120+ };
121+
99122 template <class F >
100123 struct FunctionInvoker : public Invoker {
101124 FunctionInvoker (F func)
@@ -134,6 +157,11 @@ Callback<R, Arg> bind_callback(R (T::*func)(Arg), T* object) {
134157 return Callback<R, Arg>(func, object);
135158}
136159
160+ template <class R , class Arg , class T >
161+ Callback<R, Arg> bind_callback (R (T::*func)(Arg), const SharedRefPtr<T>& ptr) {
162+ return Callback<R, Arg>(func, ptr);
163+ }
164+
137165template <class R , class Arg >
138166Callback<R, Arg> bind_callback (R (*func)(Arg)) {
139167 return Callback<R, Arg>(func);
0 commit comments