--- ~~Title: Events Programming Guide~~ ~~NOCACHE~~ --- # Events Programming Guide # EFL is event-driven. This means that execution usually takes place within an internal EFL *Main Loop*. The application receives notifications through function callbacks. These can apply to virtually any event which occurs on a computer. Events play a central role in EFL. In this guide, you'll learn more about the required methods to handle them. You can also find usage examples in the EFL examples repository: [reference/c/core/src/core_event.c](https://git.enlightenment.org/enlightenment/examples/src/branch/master/reference/c/core/src/core_event.c) ## Prerequisites ## * Read the [Introduction to Eo](/develop/tutorials/c/eo-intro.md) to understand how Eo objects are created and destroyed. ## Listening to Events from Objects ## All Eo objects can emit events. You can discover more about this in the Events sections of their respective [API Reference documentation](/develop/api/). To register a callback method to be called when an object emits a given event use ``efl_event_callback_add()``: ```c efl_event_callback_add(object, event, callback, data); ``` Substitute *object* for any ``Eo *`` or derived object and *event* for the identifier of the event (such as ``EFL_LOOP_EVENT_POLL_HIGH`` or ``EFL_LOOP_TIMER_EVENT_TIMER_TICK``). Set *callback* to the method to be called when the event occurs and *data* to any data you want to pass to your callback (if you have no need of this use ``NULL``). The method signature for the callback is: ```c void callback(void *data, const Efl_Event *event); ``` In the above example *data* is the last parameter you used when registering the callback with ``efl_event_callback_add()``. *event* contains information about the event itself: | Attribute | Type | Content | | --------------------- | ---------------- | --------------------------------- | | ``event->object`` | ``Eo *`` | The Object that emitted the event | | ``event->info`` | ``void *`` | Used by some events to provide additional information. Must be cast to the appropriate type (see below). | | ``event->desc->name`` | ``const char *`` | Name of the event | The [API Reference documentation](/develop/api/) for each event tells you how to use ``event->info``. See [EFL_EVENT_POINTER_DOWN](/develop/api/efl/input/interface/event/pointer_down) for more examples. To stop receiving notifications for a particular event (unregister a callback) use ``efl_event_callback_del()``: ```c efl_event_callback_del(object, event, callback, data); ``` The parameters here have the same meaning as for ``efl_event_callback_add()``. Note that in order to unregister the callback you have to provide **the same parameters** you used to register it. This is because you can register different callbacks to the same event or even the same callback with different *data*. > **NOTE:** > Registering and unregistering callbacks is an resource-intensive process. If you perform these operations continuously on several callbacks at the same time do so in a batch as this is more efficient. You can use ``efl_event_callback_array_add()`` and ``efl_event_callback_array_del()`` to accomplish this. Remember however that you can't unregister an individual callback which has been registered in a batch. They must all be unregistered together. Below is an example code snippet based on [reference/c/core/src/core_event.c](https://git.enlightenment.org/enlightenment/examples/src/branch/master/reference/c/core/src/core_event.c): ```c static void callback(void *data, const Efl_Event *event) { Efl_Loop *polled = data; printf(" Polled %s from %s\n", efl_name_get(polled), efl_name_get(event->object)); } void setup() { [...] efl_add(EFL_LOOP_TIMER_CLASS, mainloop, efl_name_set(efl_added, "timer2"), efl_loop_timer_interval_set(efl_added, .1), efl_event_callback_add(efl_added, EFL_LOOP_TIMER_EVENT_TIMER_TICK, callback, mainloop)); [...] } ``` Here a new timer object is created and added to ``mainloop``. The configuration of this timer takes place entirely inside the ``efl_add()`` call, as explained in the [Introduction to Eo](/develop/tutorials/c/eo-intro.md) tutorial. Note how the ``polled`` object is passed as the *data* parameter to ``efl_event_callback_add()`` and recovered from the callback. The object that emitted the event (the timer) is also recovered from the callback through the ``event`` parameter. ## Pausing and Resuming Event Notifications ## All event emissions from a given object can be paused (*frozen*) using ``efl_event_freeze()`` and resumed with ``efl_event_thaw()``: ```c efl_event_freeze(object); efl_event_thaw(object); ``` While an object is frozen only high-priority events (marked as *hot*) will be emitted. Hot events cannot be stopped. Remember that ALL events emitting from a object are stopped if its frozen, except for hot events. If you need to stop individual events you can unregister their callback temporarily and then re-register later. ## Defining Custom Events ## You can define any number of custom events and emit them from any Eo object. You can then register callbacks to be activated by these events. First create a ``Efl_Event_Description`` variable. Next, initialize it with ``EFL_EVENT_DESCRIPTION()`` and make it available everywhere you want to use this new event: ```c Efl_Event_Description CUSTOM_EVENT = EFL_EVENT_DESCRIPTION("custom-event"); ``` Register to this event as you would normally do for EFL events with ``efl_event_callback_add()``: ```c efl_event_callback_add(object, &CUSTOM_EVENT, callback, data); ``` *data* works as usual and can be recovered from the callback through the ``data`` parameter. Now emit the event using ``efl_event_callback_call()``: ```c efl_event_callback_call(object, &CUSTOM_EVENT, event_info); ``` *event_info* will be passed to the callback through the ``event->info`` parameter. Its meaning is completely up to you as the event creator. ## Further Reading ## [reference/c/core/src/core_event.c](https://git.enlightenment.org/enlightenment/examples/src/branch/master/reference/c/core/src/core_event.c) : EFL examples repository [``Efl.Object`` API Reference](/develop/api/efl/object) : Detailed documentation for the EFL object, which implements the events mechanism [Introduction to Eo](/develop/tutorials/c/eo-intro.md) : Tutorial on instantiating and configuring Eo objects