8 #include "ecore_private.h"
10 static int inpurge = 0;
12 struct _Ecore_Event_Handler
17 Ecore_Event_Handler_Cb func;
20 Eina_Bool delete_me : 1;
23 struct _Ecore_Event_Filter
27 Ecore_Data_Cb func_start;
28 Ecore_Filter_Cb func_filter;
29 Ecore_End_Cb func_end;
33 Eina_Bool delete_me : 1;
42 Ecore_End_Cb func_free;
45 Eina_Bool delete_me : 1;
49 static int events_num = 0;
50 static Ecore_Event *events = NULL;
51 static Ecore_Event *event_current = NULL;
52 static Ecore_Event *purge_events = NULL;
54 static Ecore_Event_Handler **event_handlers = NULL;
55 static Ecore_Event_Handler *event_handler_current = NULL;
56 static int event_handlers_num = 0;
57 static int event_handlers_alloc_num = 0;
58 static Eina_List *event_handlers_delete_list = NULL;
60 static Ecore_Event_Handler *event_handlers_add_list = NULL;
62 static Ecore_Event_Filter *event_filters = NULL;
63 static Ecore_Event_Filter *event_filter_current = NULL;
64 static Ecore_Event *event_filter_event_current = NULL;
65 static int event_filters_delete_me = 0;
66 static int event_id_max = ECORE_EVENT_COUNT;
67 static int ecore_raw_event_type = ECORE_EVENT_NONE;
68 static void *ecore_raw_event_event = NULL;
71 static void _ecore_event_purge_deleted(void);
72 static void *_ecore_event_del(Ecore_Event *event);
76 * @addtogroup Ecore_Group Ecore - Main Loop and Job Functions.
82 * @addtogroup Ecore_Event_Group Ecore Event functions
88 * Add an event handler.
89 * @param type The type of the event this handler will get called for
90 * @param func The function to call when the event is found in the queue
91 * @param data A data pointer to pass to the called function @p func
92 * @return A new Event handler, or NULL on failure
94 * Add an event handler to the list of handlers. This will, on success, return
95 * a handle to the event handler object that was created, that can be used
96 * later to remove the handler using ecore_event_handler_del(). The @p type
97 * parameter is the integer of the event type that will trigger this callback
98 * to be called. The callback @p func is called when this event is processed
99 * and will be passed the event type, a pointer to the private event
100 * structure that is specific to that event type, and a data pointer that is
101 * provided in this call as the @p data parameter.
103 * When the callback @p func is called, it must return 1 or 0. If it returns
104 * 1 (or ECORE_CALLBACK_RENEW), It will keep being called as per normal, for
105 * each handler set up for that event type. If it returns 0 (or
106 * ECORE_CALLBACK_CANCEL), it will cease processing handlers for that particular
107 * event, so all handler set to handle that event type that have not already
108 * been called, will not be.
110 EAPI Ecore_Event_Handler *
111 ecore_event_handler_add(int type, Ecore_Event_Handler_Cb func, const void *data)
113 Ecore_Event_Handler *eh;
115 if (!func) return NULL;
116 if ((type <= ECORE_EVENT_NONE) || (type >= event_id_max)) return NULL;
117 eh = calloc(1, sizeof(Ecore_Event_Handler));
118 if (!eh) return NULL;
119 ECORE_MAGIC_SET(eh, ECORE_MAGIC_EVENT_HANDLER);
122 eh->data = (void *)data;
123 if (type >= (event_handlers_num - 1))
127 p_alloc_num = event_handlers_alloc_num;
128 event_handlers_num = type + 1;
129 if (event_handlers_num > event_handlers_alloc_num)
131 Ecore_Event_Handler **new_handlers;
134 event_handlers_alloc_num = ((event_handlers_num + 16) / 16) * 16;
135 new_handlers = realloc(event_handlers, event_handlers_alloc_num * sizeof(Ecore_Event_Handler *));
141 event_handlers = new_handlers;
142 for (i = p_alloc_num; i < event_handlers_alloc_num; i++)
143 event_handlers[i] = NULL;
146 if (ecore_raw_event_type == type)
147 event_handlers_add_list = (Ecore_Event_Handler *)eina_inlist_append(EINA_INLIST_GET(event_handlers_add_list), EINA_INLIST_GET(eh));
148 else if (type < event_handlers_alloc_num)
149 event_handlers[type] = (Ecore_Event_Handler *)eina_inlist_append(EINA_INLIST_GET(event_handlers[type]), EINA_INLIST_GET(eh));
154 * Delete an event handler.
155 * @param event_handler Event handler handle to delete
156 * @return Data passed to handler
158 * Delete a specified event handler from the handler list. On success this will
159 * delete the event handler and return the pointer passed as @p data when the
160 * handler was added by ecore_event_handler_add(). On failure NULL will be
161 * returned. Once a handler is deleted it will no longer be called.
164 ecore_event_handler_del(Ecore_Event_Handler *event_handler)
166 if (!ECORE_MAGIC_CHECK(event_handler, ECORE_MAGIC_EVENT_HANDLER))
168 ECORE_MAGIC_FAIL(event_handler, ECORE_MAGIC_EVENT_HANDLER,
169 "ecore_event_handler_del");
172 EINA_SAFETY_ON_TRUE_RETURN_VAL(event_handler->delete_me, NULL);
173 event_handler->delete_me = 1;
174 event_handlers_delete_list = eina_list_append(event_handlers_delete_list, event_handler);
175 return event_handler->data;
179 * @brief Get the data associated with an #Ecore_Event_Handler
180 * @param eh The event handler
182 * This function returns the data previously associated with @p eh.
185 ecore_event_handler_data_get(Ecore_Event_Handler *eh)
187 if (!ECORE_MAGIC_CHECK(eh, ECORE_MAGIC_EVENT_HANDLER))
189 ECORE_MAGIC_FAIL(eh, ECORE_MAGIC_EVENT_HANDLER, "ecore_event_handler_data_get");
196 * @brief Set the data associated with an #Ecore_Event_Handler
197 * @param eh The event handler
198 * @param data The data to associate
199 * @return The previous data
200 * This function sets @p data to @p eh and returns the old data pointer
201 * which was previously associated with @p eh.
204 ecore_event_handler_data_set(Ecore_Event_Handler *eh, void *data)
207 if (!ECORE_MAGIC_CHECK(eh, ECORE_MAGIC_EVENT_HANDLER))
209 ECORE_MAGIC_FAIL(eh, ECORE_MAGIC_EVENT_HANDLER, "ecore_event_handler_data_set");
218 _ecore_event_generic_free (void *data __UNUSED__, void *event)
224 * Add an event to the event queue.
225 * @param type The event type to add to the end of the event queue
226 * @param ev The private data structure for this event type
227 * @param func_free The function to be called to free this private structure
228 * @param data The data pointer to be passed to the free function
229 * @return A Handle for that event
231 * On success this function returns a handle to an event on the event queue, or
232 * NULL if it fails. If it succeeds, an event of type @p type will be added
233 * to the queue for processing by event handlers added by
234 * ecore_event_handler_add(). The @p ev parameter will be a pointer to the event
235 * private data that is specific to that event type. When the event is no
236 * longer needed, @p func_free will be called and passed the private structure
237 * pointer for cleaning up. If @p func_free is NULL, free() will be called
238 * with the private structure pointer.
239 * func_free is passed @p data as its data parameter.
242 ecore_event_add(int type, void *ev, Ecore_End_Cb func_free, void *data)
244 /* if (!ev) return NULL;*/
245 if (type <= ECORE_EVENT_NONE) return NULL;
246 if (type >= event_id_max) return NULL;
247 if ((ev) && (!func_free)) func_free = _ecore_event_generic_free;
248 return _ecore_event_add(type, ev, func_free, data);
252 * Delete an event from the queue.
253 * @param event The event handle to delete
254 * @return The data pointer originally set for the event free function
256 * This deletes the event @p event from the event queue, and returns the
257 * @p data parameer originally set when adding it with ecore_event_add(). This
258 * does not immediately call the free function, and it may be called later on
259 * cleanup, and so if the free function depends on the data pointer to work,
260 * you should defer cleaning of this till the free function is called later.
263 ecore_event_del(Ecore_Event *event)
265 if (!ECORE_MAGIC_CHECK(event, ECORE_MAGIC_EVENT))
267 ECORE_MAGIC_FAIL(event, ECORE_MAGIC_EVENT, "ecore_event_del");
270 EINA_SAFETY_ON_TRUE_RETURN_VAL(event->delete_me, NULL);
271 event->delete_me = 1;
276 * Allocate a new event type id sensibly and return the new id.
277 * @return A new event type id.
279 * This function allocates a new event type id and returns it. Once an event
280 * type has been allocated it can never be de-allocated during the life of
281 * the program. There is no guarantee of the contents of this event ID, or how
282 * it is calculated, except that the ID will be unique to the current instance
286 ecore_event_type_new(void)
289 return event_id_max - 1;
293 * Add a filter the current event queue.
294 * @param func_start Function to call just before filtering and return data
295 * @param func_filter Function to call on each event
296 * @param func_end Function to call after the queu has been filtered
297 * @param data Data to pass to the filter functions
298 * @return A filter handle
300 * This adds a filter to call callbacks to loop through the event queue and
301 * filter events out of the queue. On failure NULL is returned. On success a
302 * Filter handle is returned. Filters are called on the queue just before
303 * Event handler processing to try and remove redundant events. Just as
304 * processing starts @p func_start is called and passed the @p data pointer.
305 * This function returns a pointer that is used as loop_data that is now passed to
306 * @p func_filter as loop_data. @p func_filter is also passed @p data and the
307 * event type and private event structure. If this callback returns 0, the
308 * event is removed from the queue. If it returns 1, the event is kept. When
309 * processing is finished @p func_end is called and is passed the loop_data
310 * and @p data pointer to clean up.
312 EAPI Ecore_Event_Filter *
313 ecore_event_filter_add(Ecore_Data_Cb func_start, Ecore_Filter_Cb func_filter, Ecore_End_Cb func_end, const void *data)
315 Ecore_Event_Filter *ef;
317 if (!func_filter) return NULL;
318 ef = calloc(1, sizeof(Ecore_Event_Filter));
319 if (!ef) return NULL;
320 ECORE_MAGIC_SET(ef, ECORE_MAGIC_EVENT_FILTER);
321 ef->func_start = func_start;
322 ef->func_filter = func_filter;
323 ef->func_end = func_end;
324 ef->data = (void *)data;
325 event_filters = (Ecore_Event_Filter *) eina_inlist_append(EINA_INLIST_GET(event_filters), EINA_INLIST_GET(ef));
330 * Delete an event filter.
331 * @param ef The event filter handle
332 * @return The data set for the filter
334 * Delete a filter that has been added by its @p ef handle. On success this
335 * will return the data pointer set when this filter was added. On failure
339 ecore_event_filter_del(Ecore_Event_Filter *ef)
341 if (!ECORE_MAGIC_CHECK(ef, ECORE_MAGIC_EVENT_FILTER))
343 ECORE_MAGIC_FAIL(ef, ECORE_MAGIC_EVENT_FILTER, "ecore_event_filter_del");
346 EINA_SAFETY_ON_TRUE_RETURN_VAL(ef->delete_me, NULL);
348 event_filters_delete_me = 1;
353 * Return the current event type being handled.
354 * @return The current event type being handled if inside a handler callback
356 * If the program is currently inside an Ecore event handler callback this
357 * will return the type of the current event being processed. If Ecore is
358 * not inside an event handler, ECORE_EVENT_NONE is returned.
360 * This is useful when certain Ecore modules such as Ecore_Evas "swallow"
361 * events and not all the original information is passed on. In special cases
362 * this extra information may be useful or needed and using this call can let
363 * the program know if the event type being handled is one it wants to get more
367 ecore_event_current_type_get(void)
369 return ecore_raw_event_type;
373 * Return the current event type pointer handled.
374 * @return The current event pointer being handled if inside a handler callback
376 * If the program is currently inside an Ecore event handler callback this
377 * will return the pointer of the current event being processed. If Ecore is
378 * not inside an event handler, NULL will be returned.
380 * This is useful when certain Ecore modules such as Ecore_Evas "swallow"
381 * events and not all the original information is passed on. In special cases
382 * this extra information may be useful or needed and using this call can let
383 * the program access the event data if the type of the event is handled by
387 ecore_event_current_event_get(void)
389 return ecore_raw_event_event;
401 _ecore_event_shutdown(void)
404 Ecore_Event_Handler *eh;
405 Ecore_Event_Filter *ef;
407 while (events) _ecore_event_del(events);
408 event_current = NULL;
409 for (i = 0; i < event_handlers_num; i++)
411 while ((eh = event_handlers[i]))
413 event_handlers[i] = (Ecore_Event_Handler *) eina_inlist_remove(EINA_INLIST_GET(event_handlers[i]), EINA_INLIST_GET(event_handlers[i]));
414 ECORE_MAGIC_SET(eh, ECORE_MAGIC_NONE);
415 if (!eh->delete_me) free(eh);
418 EINA_LIST_FREE(event_handlers_delete_list, eh)
420 if (event_handlers) free(event_handlers);
421 event_handlers = NULL;
422 event_handlers_num = 0;
423 event_handlers_alloc_num = 0;
424 while ((ef = event_filters))
426 event_filters = (Ecore_Event_Filter *) eina_inlist_remove(EINA_INLIST_GET(event_filters), EINA_INLIST_GET(event_filters));
427 ECORE_MAGIC_SET(ef, ECORE_MAGIC_NONE);
430 event_filters_delete_me = 0;
431 event_filter_current = NULL;
432 event_filter_event_current = NULL;
436 _ecore_event_exist(void)
439 EINA_INLIST_FOREACH(events, e)
440 if (!e->delete_me) return 1;
445 _ecore_event_add(int type, void *ev, Ecore_End_Cb func_free, void *data)
449 e = calloc(1, sizeof(Ecore_Event));
451 ECORE_MAGIC_SET(e, ECORE_MAGIC_EVENT);
454 e->func_free = func_free;
458 purge_events = (Ecore_Event *)eina_inlist_append(EINA_INLIST_GET(purge_events), EINA_INLIST_GET(e));
463 events = (Ecore_Event *)eina_inlist_append(EINA_INLIST_GET(events), EINA_INLIST_GET(e));
470 _ecore_event_del(Ecore_Event *event)
475 if (event->func_free) event->func_free(event->data, event->event);
476 events = (Ecore_Event *) eina_inlist_remove(EINA_INLIST_GET(events), EINA_INLIST_GET(event));
477 ECORE_MAGIC_SET(event, ECORE_MAGIC_NONE);
484 _ecore_event_purge_deleted(void)
486 Ecore_Event *itr = events;
491 Ecore_Event *next = (Ecore_Event *)EINA_INLIST_GET(itr)->next;
492 if ((!itr->references) && (itr->delete_me))
493 _ecore_event_del(itr);
499 Ecore_Event *e = purge_events;
500 purge_events = (Ecore_Event *)eina_inlist_remove(EINA_INLIST_GET(purge_events), EINA_INLIST_GET(purge_events));
501 events = (Ecore_Event *)eina_inlist_append(EINA_INLIST_GET(events), EINA_INLIST_GET(e));
506 _ecore_event_filters_apply()
509 if (!event_filter_current)
511 /* regular main loop, start from head */
512 event_filter_current = event_filters;
516 /* recursive main loop, continue from where we were */
517 event_filter_current = (Ecore_Event_Filter *)EINA_INLIST_GET(event_filter_current)->next;
520 while (event_filter_current)
522 Ecore_Event_Filter *ef = event_filter_current;
529 ef->loop_data = ef->func_start(ef->data);
531 if (!event_filter_event_current)
533 /* regular main loop, start from head */
534 event_filter_event_current = events;
538 /* recursive main loop, continue from where we were */
539 event_filter_event_current = (Ecore_Event *)EINA_INLIST_GET(event_filter_event_current)->next;
542 while (event_filter_event_current)
544 Ecore_Event *e = event_filter_event_current;
546 if (!ef->func_filter(ef->data, ef->loop_data,
552 if (event_filter_event_current) /* may have changed in recursive main loops */
553 event_filter_event_current = (Ecore_Event *)EINA_INLIST_GET(event_filter_event_current)->next;
556 ef->func_end(ef->data, ef->loop_data);
561 if (event_filter_current) /* may have changed in recursive main loops */
562 event_filter_current = (Ecore_Event_Filter *)EINA_INLIST_GET(event_filter_current)->next;
564 if (event_filters_delete_me)
566 int deleted_in_use = 0;
567 Ecore_Event_Filter *l;
568 for (l = event_filters; l;)
570 Ecore_Event_Filter *ef = l;
571 l = (Ecore_Event_Filter *) EINA_INLIST_GET(l)->next;
580 event_filters = (Ecore_Event_Filter *) eina_inlist_remove(EINA_INLIST_GET(event_filters), EINA_INLIST_GET(ef));
581 ECORE_MAGIC_SET(ef, ECORE_MAGIC_NONE);
586 event_filters_delete_me = 0;
590 _ecore_event_call(void)
592 Eina_List *l, *l_next;
593 Ecore_Event_Handler *eh;
595 _ecore_event_filters_apply();
599 /* regular main loop, start from head */
600 event_current = events;
601 event_handler_current = NULL;
604 while (event_current)
606 Ecore_Event *e = event_current;
607 int handle_count = 0;
611 event_current = (Ecore_Event *)EINA_INLIST_GET(event_current)->next;
615 ecore_raw_event_type = e->type;
616 ecore_raw_event_event = e->event;
618 if ((e->type >= 0) && (e->type < event_handlers_num))
620 if (!event_handler_current)
622 /* regular main loop, start from head */
623 event_handler_current = event_handlers[e->type];
627 /* recursive main loop, continue from where we were */
628 event_handler_current = (Ecore_Event_Handler *)EINA_INLIST_GET(event_handler_current)->next;
631 while ((event_handler_current) && (!e->delete_me))
633 eh = event_handler_current;
641 ret = eh->func(eh->data, e->type, e->event);
646 event_handler_current = NULL;
647 break; /* 0 == "call no further handlers" */
651 if (event_handler_current) /* may have changed in recursive main loops */
652 event_handler_current = (Ecore_Event_Handler *)EINA_INLIST_GET(event_handler_current)->next;
655 while (event_handlers_add_list)
657 eh = event_handlers_add_list;
658 event_handlers_add_list = (Ecore_Event_Handler *)eina_inlist_remove(EINA_INLIST_GET(event_handlers_add_list), EINA_INLIST_GET(eh));
659 event_handlers[eh->type] = (Ecore_Event_Handler *)eina_inlist_append(EINA_INLIST_GET(event_handlers[eh->type]), EINA_INLIST_GET(eh));
661 /* if no handlers were set for EXIT signal - then default is */
662 /* to quit the main loop */
663 if ((e->type == ECORE_EVENT_SIGNAL_EXIT) && (handle_count == 0))
664 ecore_main_loop_quit();
668 if (event_current) /* may have changed in recursive main loops */
669 event_current = (Ecore_Event *)EINA_INLIST_GET(event_current)->next;
672 ecore_raw_event_type = ECORE_EVENT_NONE;
673 ecore_raw_event_event = NULL;
675 _ecore_event_purge_deleted();
677 EINA_LIST_FOREACH_SAFE(event_handlers_delete_list, l, l_next, eh)
679 if (eh->references) continue;
681 event_handlers_delete_list = eina_list_remove_list(event_handlers_delete_list, l);
683 event_handlers[eh->type] = (Ecore_Event_Handler *) eina_inlist_remove(EINA_INLIST_GET(event_handlers[eh->type]), EINA_INLIST_GET(eh));
684 ECORE_MAGIC_SET(eh, ECORE_MAGIC_NONE);
690 _ecore_event_signal_user_new(void)
692 Ecore_Event_Signal_User *e;
694 e = calloc(1, sizeof(Ecore_Event_Signal_User));
699 _ecore_event_signal_hup_new(void)
701 Ecore_Event_Signal_Hup *e;
703 e = calloc(1, sizeof(Ecore_Event_Signal_Hup));
708 _ecore_event_signal_exit_new(void)
710 Ecore_Event_Signal_Exit *e;
712 e = calloc(1, sizeof(Ecore_Event_Signal_Exit));
717 _ecore_event_signal_power_new(void)
719 Ecore_Event_Signal_Power *e;
721 e = calloc(1, sizeof(Ecore_Event_Signal_Power));
726 _ecore_event_signal_realtime_new(void)
728 return calloc(1, sizeof(Ecore_Event_Signal_Realtime));