c33b2441ac15dbae2591e82e9588cdcfc4b69d50
[framework/uifw/ecore.git] / src / lib / ecore / ecore_events.c
1 #include "ecore_private.h"
2 #include "Ecore.h"
3
4 static int                  events_num = 0;
5 static Ecore_Event         *events = NULL;
6
7 static Ecore_Event_Handler **event_handlers = NULL;
8 static int                   event_handlers_num = 0;
9 static int                   event_handlers_alloc_num = 0;
10 static Ecore_List2_Data     *event_handlers_delete_list = NULL;
11
12 static Ecore_Event_Filter  *event_filters = NULL;
13 static int                  event_filters_delete_me = 0;
14
15 static int                  event_id_max = ECORE_EVENT_COUNT;
16
17 static int                  ecore_raw_event_type = ECORE_EVENT_NONE;
18 static void                *ecore_raw_event_event =  NULL;
19
20
21 /**
22  * Add an event handler.
23  * @param type The type of the event this handler will get called for
24  * @param func The function to call when the event is found in the queue
25  * @param data A data pointer to pass to the called function @p func
26  * @return A new Event handler, or NULL on failure
27  * 
28  * Add an event handler to the list of handlers. This will, on success, return
29  * a handle to the event handler object that was created, that can be used
30  * later to remove the handler using ecore_event_handler_del(). The @p type 
31  * parameter is the iteger of the event type that will trigger this callback
32  * to be called. The callback @p func is called when this event is processed
33  * and will be passed the event type, a pointer to the private event
34  * structure that is specific to that event type, and a data pointer that is 
35  * provided in this call as the @p data parameter.
36  * 
37  * When the callback @p func is called, it must return 1 or 0. If it returns 
38  * 1 (or ECORE_CALLBACK_RENEW), It will keep being called as per normal, for 
39  * each handler set up for that event type. If it returns 0 (or 
40  * ECORE_CALLBACK_CANCEL), it will cease processing handlers for that particular
41  * event, so all handler set to handle that event type that have not already 
42  * been called, will not be.
43  */
44 EAPI Ecore_Event_Handler *
45 ecore_event_handler_add(int type, int (*func) (void *data, int type, void *event), const void *data)
46 {
47    Ecore_Event_Handler *eh;
48
49    if (!func) return NULL;
50    if ((type <= ECORE_EVENT_NONE) || (type >= event_id_max)) return NULL;
51    eh = calloc(1, sizeof(Ecore_Event_Handler));
52    if (!eh) return NULL;
53    ECORE_MAGIC_SET(eh, ECORE_MAGIC_EVENT_HANDLER);
54    eh->type = type;
55    eh->func = func;
56    eh->data = (void *)data;
57    if (type >= (event_handlers_num - 1))
58      {
59         int p_alloc_num;
60         
61         p_alloc_num = event_handlers_alloc_num;
62         event_handlers_num = type + 1;
63         if (event_handlers_num > event_handlers_alloc_num)
64           {
65              Ecore_Event_Handler **new_handlers;
66              int i;
67              
68              event_handlers_alloc_num = ((event_handlers_num + 16) / 16) * 16;
69              new_handlers = realloc(event_handlers, event_handlers_alloc_num * sizeof(Ecore_Event_Handler *));
70              if (!new_handlers)
71                {
72                   free(eh);
73                   return NULL;
74                }
75              event_handlers = new_handlers;
76              for (i = p_alloc_num; i < event_handlers_alloc_num; i++)
77                event_handlers[i] = NULL;
78           }
79      }
80    event_handlers[type] = _ecore_list2_append(event_handlers[type], eh);
81    return eh;
82 }
83
84 /**
85  * Delete an event handler.
86  * @param event_handler Event handler handle to delete
87  * @return Data passed to handler
88  * 
89  * Delete a specified event handler from the handler list. On success this will
90  * delete the event handler and return the pointer passed as @p data when the
91  * handler was added by ecore_event_handler_add(). On failure NULL will be
92  * returned. Once a handler is deleted it will no longer be called.
93  */
94 EAPI void *
95 ecore_event_handler_del(Ecore_Event_Handler *event_handler)
96 {
97    Ecore_List2_Data *node;
98    
99    if (!ECORE_MAGIC_CHECK(event_handler, ECORE_MAGIC_EVENT_HANDLER)) 
100      {
101         ECORE_MAGIC_FAIL(event_handler, ECORE_MAGIC_EVENT_HANDLER,
102                          "ecore_event_handler_del");
103         return NULL;
104      }
105    event_handler->delete_me = 1;
106    node = calloc(1, sizeof(Ecore_List2_Data));
107    node->data = event_handler;
108    event_handlers_delete_list = _ecore_list2_append(event_handlers_delete_list, node);
109    return event_handler->data;
110 }
111
112 static void 
113 _ecore_event_generic_free (void *data __UNUSED__, void *event)
114 {
115    free (event);
116 }
117
118 /**
119  * Add an event to the event queue.
120  * @param type The event type to add to the end of the event queue
121  * @param ev The private data structure for this event type
122  * @param func_free The function to be called to free this private structure
123  * @param data The data pointer to be passed to the free function
124  * @return A Handle for that event
125  * 
126  * On success this function returns a handle to an event on the event queue, or
127  * NULL if it fails. If it succeeds, an event of type @p type will be added
128  * to the queue for processing by event handlers added by 
129  * ecore_event_handler_add(). The @p ev parameter will be a pointer to the event
130  * private data that is specific to that event type. When the event is no
131  * longer needed, @p func_free will be called and passed the private structure
132  * pointer for cleaning up. If @p func_free is NULL, free() will be called
133  * with the private structure pointer.
134  * func_free is passed @p data as its data parameter.
135  */
136 EAPI Ecore_Event *
137 ecore_event_add(int type, void *ev, void (*func_free) (void *data, void *ev), void *data)
138 {
139 /*   if (!ev) return NULL;*/
140    if (type <= ECORE_EVENT_NONE) return NULL;
141    if (type >= event_id_max) return NULL;
142    if ((ev) && (!func_free)) func_free = _ecore_event_generic_free;
143    return _ecore_event_add(type, ev, func_free, data);
144 }
145
146 /**
147  * Delete an event from the queue.
148  * @param event The event handle to delete
149  * @return The data pointer originally set for the event free function
150  * 
151  * This deletes the event @p event from the event queue, and returns the
152  * @p data parameer originally set when adding it with ecore_event_add(). This
153  * does not immediately call the free function, and it may be called later on
154  * cleanup, and so if the free function depends on the data pointer to work,
155  * you should defer cleaning of this till the free function is called later.
156  */
157 EAPI void *
158 ecore_event_del(Ecore_Event *event)
159 {
160    if (!ECORE_MAGIC_CHECK(event, ECORE_MAGIC_EVENT)) 
161      {
162         ECORE_MAGIC_FAIL(event, ECORE_MAGIC_EVENT, "ecore_event_del");  
163         return NULL;
164      }
165    event->delete_me = 1;
166    return event->data;
167 }
168
169 /**
170  * Allocate a new event type id sensibly and return the new id.
171  * @return A new event type id.
172  * 
173  * This function allocates a new event type id and returns it. Once an event 
174  * type has been allocated it can never be de-allocated during the life of
175  * the program. There is no guarantee of the contents of this event ID, or how
176  * it is calculated, except that the ID will be unique to the current instance
177  * of the process.
178  */
179 EAPI int
180 ecore_event_type_new(void)
181 {
182    event_id_max++;
183    return event_id_max - 1;
184 }
185
186 /**
187  * Add a filter the current event queue.
188  * @param func_start Function to call just before filtering and return data
189  * @param func_filter Function to call on each event
190  * @param func_end Function to call after the queu has been filtered
191  * @param data Data to pass to the filter functions
192  * @return A filter handle
193  * 
194  * This adds a filter to call callbacks to loop through the event queue and 
195  * filter events out of the queue. On failure NULL is returned. On success a
196  * Filter handle is returned. Filters are called on the queue just before
197  * Event handler processing to try and remove redundant events. Just as
198  * processing starts @p func_start is called and passed the @p data pointer.
199  * This function returns a pointer that is used as loop_data that is now passed to
200  * @p func_filter as loop_data. @p func_filter is also passed @p data and the
201  * event type and private event structure. If this callback returns 0, the
202  * event is removed from the queue. If it returns 1, the event is kept. When
203  * processing is finished @p func_end is called and is passed the loop_data
204  * and @p data pointer to clean up.
205  */
206 EAPI Ecore_Event_Filter *
207 ecore_event_filter_add(void * (*func_start) (void *data), int (*func_filter) (void *data, void *loop_data, int type, void *event), void (*func_end) (void *data, void *loop_data), const void *data)
208 {
209    Ecore_Event_Filter *ef;
210    
211    if (!func_filter) return NULL;
212    ef = calloc(1, sizeof(Ecore_Event_Filter));
213    if (!ef) return NULL;
214    ECORE_MAGIC_SET(ef, ECORE_MAGIC_EVENT_FILTER);
215    ef->func_start = func_start;
216    ef->func_filter = func_filter;
217    ef->func_end = func_end;
218    ef->data = (void *)data;
219    event_filters = _ecore_list2_append(event_filters, ef);
220    return ef;
221 }
222
223 /**
224  * Delete an event filter.
225  * @param ef The event filter handle
226  * @return The data set for the filter
227  * 
228  * Delete a filter that has been added by its @p ef handle. On success this
229  * will return the data pointer set when this filter was added. On failure
230  * NULL is returned.
231  */
232 EAPI void *
233 ecore_event_filter_del(Ecore_Event_Filter *ef)
234 {   
235    if (!ECORE_MAGIC_CHECK(ef, ECORE_MAGIC_EVENT_FILTER))
236      {
237         ECORE_MAGIC_FAIL(ef, ECORE_MAGIC_EVENT_FILTER, "ecore_event_filter_del");
238         return NULL;
239      }
240    ef->delete_me = 1;
241    event_filters_delete_me = 1;
242    return ef->data;
243 }
244
245 /**
246  * Return the current event type being handled.
247  * @return The current event type being handled if inside a handler callback
248  * 
249  * If the program is currently inside an Ecore event handler callback this
250  * will return the type of the current event being processed. If Ecore is
251  * not inside an event handler, ECORE_EVENT_NONE is returned.
252  * 
253  * This is useful when certain Ecore modules such as Ecore_Evas "swallow"
254  * events and not all the original information is passed on. In special cases
255  * this extra information may be useful or needed and using this call can let
256  * the program know if the event type being handled is one it wants to get more
257  * information about.
258  */
259 EAPI int
260 ecore_event_current_type_get(void)
261 {
262    return ecore_raw_event_type;
263 }
264
265 /**
266  * Return the current event type pointer handled.
267  * @return The current event pointer being handled if inside a handler callback
268  * 
269  * If the program is currently inside an Ecore event handler callback this
270  * will return the pointer of the current event being processed. If Ecore is
271  * not inside an event handler, NULL will be returned.
272  * 
273  * This is useful when certain Ecore modules such as Ecore_Evas "swallow"
274  * events and not all the original information is passed on. In special cases
275  * this extra information may be useful or needed and using this call can let
276  * the program access the event data if the type of the event is handled by
277  * the program.
278  */
279 EAPI void *
280 ecore_event_current_event_get(void)
281 {
282    return ecore_raw_event_event;
283 }
284
285 void
286 _ecore_event_shutdown(void)
287 {
288    int i;
289    
290    while (events) _ecore_event_del(events);
291    for (i = 0; i < event_handlers_num; i++)
292      {
293         while (event_handlers[i])
294           {
295              Ecore_Event_Handler *eh;
296              
297              eh = event_handlers[i];
298              event_handlers[i] = _ecore_list2_remove(event_handlers[i], eh);
299              ECORE_MAGIC_SET(eh, ECORE_MAGIC_NONE);
300              free(eh);
301           }
302      }
303    while (event_handlers_delete_list)
304      {
305         Ecore_List2_Data *ehd;
306         
307         ehd = event_handlers_delete_list;
308         event_handlers_delete_list = _ecore_list2_remove(event_handlers_delete_list, ehd);
309         free(ehd);
310      }
311    if (event_handlers) free(event_handlers);
312    event_handlers = NULL;
313    event_handlers_num = 0;
314    event_handlers_alloc_num = 0;
315    while (event_filters)
316      {
317         Ecore_Event_Filter *ef;
318         
319         ef = event_filters;
320         event_filters = _ecore_list2_remove(event_filters, ef);   
321         ECORE_MAGIC_SET(ef, ECORE_MAGIC_NONE);
322         free(ef);
323      }
324    event_filters_delete_me = 0;
325 }
326
327 int
328 _ecore_event_exist(void)
329 {
330    if (events) return 1;
331    return 0;
332 }
333
334 Ecore_Event *
335 _ecore_event_add(int type, void *ev, void (*func_free) (void *data, void *ev), void *data)
336 {
337    Ecore_Event *e;
338    
339    e = calloc(1, sizeof(Ecore_Event));
340    if (!e) return NULL;
341    ECORE_MAGIC_SET(e, ECORE_MAGIC_EVENT);
342    e->type = type;
343    e->event = ev;
344    e->func_free = func_free;
345    e->data = data;
346    events = _ecore_list2_append(events, e);
347    events_num++;
348    return e;
349 }
350
351 void *
352 _ecore_event_del(Ecore_Event *event)
353 {
354    void *data;
355    
356    data = event->data;
357    if (event->func_free) event->func_free(event->data, event->event);
358    events = _ecore_list2_remove(events, event);
359    ECORE_MAGIC_SET(event, ECORE_MAGIC_NONE);
360    free(event);
361    events_num--;
362    return data;
363 }
364
365 void
366 _ecore_event_call(void)
367 {
368    Ecore_List2 *l, *ll;
369    Ecore_Event *e;
370    Ecore_Event_Filter *ef;
371    Ecore_Event_Handler *eh;
372    Ecore_List2_Data *ehd;
373    int handle_count;
374
375    for (l = (Ecore_List2 *)event_filters; l; l = l->next)
376      {
377         ef = (Ecore_Event_Filter *)l;
378         if (!ef->delete_me)
379           {
380              if (ef->func_start)
381                ef->loop_data = ef->func_start(ef->data);
382              for (ll = (Ecore_List2 *)events; ll; ll = ll->next)
383                {
384                   e = (Ecore_Event *)ll;
385                   if (!ef->func_filter(ef->loop_data, ef->data,
386                                        e->type, e->event))
387                     {
388 //                     printf("FILTER SAID TO DEL ev %p\n", e->event);
389                        ecore_event_del(e);
390                     }
391                }
392              if (ef->func_end)
393                ef->func_end(ef->data, ef->loop_data);
394           }
395      }
396    if (event_filters_delete_me)
397      {
398         for (l = (Ecore_List2 *)event_filters; l;)
399           {
400              ef = (Ecore_Event_Filter *)l;
401              l = l->next;
402              if (ef->delete_me)
403                {
404                   event_filters = _ecore_list2_remove(event_filters, ef);
405                   ECORE_MAGIC_SET(ef, ECORE_MAGIC_NONE);
406                   free(ef);
407                }
408           }
409         event_filters_delete_me = 0;
410      }
411 //   printf("EVENT BATCH...\n");
412    for (l = (Ecore_List2 *)events; l; l = l->next)
413      {
414         e = (Ecore_Event *)l;
415         if (!e->delete_me)
416           {
417              handle_count = 0;
418              ecore_raw_event_type = e->type;
419              ecore_raw_event_event = e->event;
420 //           printf("HANDLE ev type %i, %p\n", e->type, e->event);
421              if ((e->type >= 0) && (e->type < event_handlers_num))
422                {
423                   for (ll = (Ecore_List2 *)event_handlers[e->type]; ll; ll = ll->next)
424                     {
425                        eh = (Ecore_Event_Handler *)ll;
426                        if (!eh->delete_me)
427                          {
428                             handle_count++;
429                             if (!eh->func(eh->data, e->type, e->event))
430                               break;  /* 0 == "call no further handlers" */
431                          }
432                     }
433                }
434              /* if no handlers were set for EXIT signal - then default is */
435              /* to quit the main loop */
436              if ((e->type == ECORE_EVENT_SIGNAL_EXIT) && (handle_count == 0))
437                ecore_main_loop_quit();
438           }
439      }
440 //   printf("EVENT BATCH DONE\n");
441    ecore_raw_event_type = ECORE_EVENT_NONE;
442    ecore_raw_event_event = NULL;
443    
444    while (events) _ecore_event_del(events);
445    while (event_handlers_delete_list)
446      {
447         ehd = event_handlers_delete_list;
448         eh = ehd->data;
449         event_handlers[eh->type] = _ecore_list2_remove(event_handlers[eh->type], eh);
450         event_handlers_delete_list = _ecore_list2_remove(event_handlers_delete_list, ehd);
451         ECORE_MAGIC_SET(eh, ECORE_MAGIC_NONE);
452         free(eh);
453         free(ehd);
454      }
455 }
456
457 EAPI void *
458 _ecore_event_signal_user_new(void)
459 {
460    Ecore_Event_Signal_User *e;
461    
462    e = calloc(1, sizeof(Ecore_Event_Signal_User));
463    return e;
464 }
465
466 void *
467 _ecore_event_signal_hup_new(void)
468 {
469    Ecore_Event_Signal_Hup *e;
470    
471    e = calloc(1, sizeof(Ecore_Event_Signal_Hup));
472    return e;
473 }
474
475 void *
476 _ecore_event_signal_exit_new(void)
477 {
478    Ecore_Event_Signal_Exit *e;
479    
480    e = calloc(1, sizeof(Ecore_Event_Signal_Exit));
481    return e;
482 }
483
484 void *
485 _ecore_event_signal_power_new(void)
486 {
487    Ecore_Event_Signal_Power *e;
488    
489    e = calloc(1, sizeof(Ecore_Event_Signal_Power));
490    return e;
491 }
492
493 void *
494 _ecore_event_signal_realtime_new(void)
495 {
496    return calloc(1, sizeof(Ecore_Event_Signal_Realtime));
497 }