11#ifndef __AUDACITY_OBSERVER__
12#define __AUDACITY_OBSERVER__
22template<
typename Message,
bool NotifyAll>
32 virtual
void OnBeginPublish() = 0;
35 virtual
bool OnEachFailedCallback() noexcept(false) = 0;
37 virtual
void OnEndPublish() noexcept(false) = 0;
46 std::shared_ptr<RecordBase>
next;
50 std::weak_ptr<RecordLink>
prev;
51 void Unlink() noexcept;
62 bool Visit(const
void *arg);
80 void Reset() noexcept;
87 bool Expired()
const {
return m_wRecord.expired(); }
90 explicit operator bool()
const {
return !Expired(); }
94 explicit Subscription(std::weak_ptr<detail::RecordBase> pRecord);
107template<
typename Message = Message,
bool NotifyAll = true>
113 static constexpr bool notifies_all = NotifyAll;
121 template<
typename Alloc = std::allocator<Record>>
143 template<
typename Object,
typename Return,
typename... Args>
145 Object &obj, Return (Object::*callback)(Args...))
147 return Subscribe( [&obj, callback](
const Message &message){
148 return (obj.*callback)(message);
170 std::shared_ptr<detail::RecordList>
m_list;
174template<
typename Message,
bool NotifyAll>
175template<
typename Alloc>
inline
177: m_list{
std::allocate_shared<
detail::RecordList>( a, pPolicy,
179 const
detail::RecordBase &recordBase, const void *arg){
180 auto &record =
static_cast<const Record&
>(recordBase);
182 auto &message = *
static_cast<const Message*
>(arg);
183 assert(record.callback);
185 if constexpr (NotifyAll)
186 return (record.callback(message),
false);
188 return record.callback(message);
191, m_factory( [a = move(a)](Callback callback) {
192 return std::allocate_shared<Record>(a, move(callback));
198template<
typename Message,
bool NotifyAll>
203 return m_list->Subscribe(m_factory(move(callback)));
206template<
typename Message,
bool NotifyAll>
inline
210 bool result = m_list->Visit(&message);
211 if constexpr (!NotifyAll)
An object that sends messages to an open-ended list of subscribed callbacks.
Subscription Subscribe(Object &obj, Return(Object::*callback)(Args...))
Overload of Subscribe takes an object and pointer-to-member-function.
Publisher(Publisher &&)=default
Subscription Subscribe(Callback callback)
Connect a callback to the Publisher; later-connected are called earlier.
std::shared_ptr< detail::RecordList > m_list
std::conditional_t< NotifyAll, void, bool > CallbackReturn
Publisher & operator=(Publisher &&)=default
std::function< std::shared_ptr< detail::RecordBase >(Callback)> m_factory
CallbackReturn Publish(const Message &message)
Send a message to connected callbacks.
Publisher(ExceptionPolicy *pPolicy=nullptr, Alloc a={})
Constructor supporting type-erased custom allocation/deletion.
std::function< CallbackReturn(const Message &) > Callback
Type of functions that can be connected to the Publisher.
A move-only handle representing a connection to a Publisher.
~Subscription() noexcept
Calls Reset.
Subscription(Subscription &&)
std::weak_ptr< detail::RecordBase > m_wRecord
TranslatableString Message(unsigned trackCount)
May be supplied to constructor of Publisher to customize exception handling.
virtual ~ExceptionPolicy() noexcept
Default message type for Publisher.
Record(Callback callback)
doubly-linked list cell using shared and weak pointers
std::weak_ptr< RecordLink > prev
std::shared_ptr< RecordBase > next
bool(*)(const RecordBase &record, const void *arg) Visitor
Type of function visiting the list; stop visit on true return.