On 25/01/2014 01:13, Quoth Bjorn Reese:
Or each "function" is just a custom async operation. You don't request a function and then try to interrogate it, you just execute operations.
Can you elaborate? If I have the following event listener, how would it look and be used with your suggestion?
class gui_event { public: virtual void on_key(int key); virtual void on_help(int x, int y); };
You flip it around. Instead of having an event listener object that is registered on some event provider source, where the provider source invokes the methods explicitly when an event arrives, you have anything that is interested in events invoke an async request on the source object. So it'd be something more like this: class gui_source { public: // actually using templates to make the callback more generic void async_key(void (*callback)(error_code ec, int key)); void async_help(void (*callback)(error_code ec, int x, int y)); }; The code on the receiving side just handles a callback instead of receiving an explicit call, but otherwise it's basically the same. You still have to externally define your threading model (eg. GUI events typically assume they're always called back on the same thread), and the policy on whether events are forwarded to all listeners or only first-come-first-served, if callbacks are supposed to be ordered in some way, and if callbacks are "persistent" (request once, called many times) or "single-shot" (one callback per request, as in ASIO), and if the latter, what happens if an event arrives when a particular listener is in between listen calls. Because of the extra complexity, it's definitely *easier* to use the direct-notifier pattern, which is why most UI frameworks do that. But it's *possible* to use these successfully even with single-shot callbacks -- just look at AJAX long-polling for a real-world example.