Hi,
This patch doesn't break anything at this time :-) It's a
standalone feature that just add the possibility to evas to receive
events from another thread. It introduce 3 new API.
* Retrieve the fd that need to be monitored by ecore :
EAPI int evas_async_events_fd_get();
* Process all pending event in the pipe (This function could be called
without any event in the pipe) :
EAPI int evas_async_events_process();
* Push an event inside the pipe from another thread :
EAPI Evas_Bool evas_async_events_put(Evas_Object *obj,
Evas_Callback_Type type, void *event_info);
I currently don't have any code using it, but I plan to use this for
the coming background loading of image. So please review it.
--
Cedric BAIL
diff --git a/src/lib/Evas.h b/src/lib/Evas.h
index e78e9a9..06f8a83 100644
--- a/src/lib/Evas.h
+++ b/src/lib/Evas.h
@@ -815,6 +815,10 @@ extern "C" {
EAPI void evas_object_event_callback_add (Evas_Object *obj, Evas_Callback_Type type, void (*func) (void *data, Evas *e, Evas_Object *obj, void *event_info), const void *data);
EAPI void *evas_object_event_callback_del (Evas_Object *obj, Evas_Callback_Type type, void (*func) (void *data, Evas *e, Evas_Object *obj, void *event_info));
+ EAPI int evas_async_events_fd_get ();
+ EAPI int evas_async_events_process ();
+ EAPI Evas_Bool evas_async_events_put (Evas_Object *obj, Evas_Callback_Type type, void *event_info);
+
EAPI void evas_object_intercept_show_callback_add (Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), const void *data);
EAPI void *evas_object_intercept_show_callback_del (Evas_Object *obj, void (*func) (void *data, Evas_Object *obj));
EAPI void evas_object_intercept_hide_callback_add (Evas_Object *obj, void (*func) (void *data, Evas_Object *obj), const void *data);
diff --git a/src/lib/canvas/Makefile.am b/src/lib/canvas/Makefile.am
index 9dda0e1..db66ba6 100644
--- a/src/lib/canvas/Makefile.am
+++ b/src/lib/canvas/Makefile.am
@@ -37,6 +37,7 @@ evas_font_dir.c \
evas_rectangle.c \
evas_render.c \
evas_smart.c \
-evas_stack.c
+evas_stack.c \
+evas_async_events.c
libevas_canvas_la_DEPENDENCIES = $(top_builddir)/config.h
diff --git a/src/lib/canvas/evas_async_events.c b/src/lib/canvas/evas_async_events.c
new file mode 100644
index 0000000..fb21c02
--- /dev/null
+++ b/src/lib/canvas/evas_async_events.c
@@ -0,0 +1,121 @@
+#include "evas_common.h"
+#include "evas_private.h"
+
+#include <unistd.h>
+#include <fcntl.h>
+#include <pthread.h>
+#include <errno.h>
+
+static int _fd_write = -1;
+static int _fd_read = -1;
+
+static int _init_evas_event = 0;
+static pthread_mutex_t _mutex;
+
+typedef struct _Evas_Event_Async Evas_Event_Async;
+struct _Evas_Event_Async
+{
+ Evas_Object *obj;
+ Evas_Callback_Type type;
+ void *event_info;
+};
+
+int
+evas_async_events_init()
+{
+ if (_init_evas_event++ == 0)
+ {
+ int filedes[2];
+
+ if (pipe(filedes) == -1)
+ {
+ _init_evas_event = 0;
+ return 0;
+ }
+
+ _fd_read = filedes[0];
+ _fd_write = filedes[1];
+
+ fcntl(_fd_read, F_SETFL, O_NONBLOCK);
+
+ pthread_mutex_init(&_mutex, NULL);
+ }
+
+ return _init_evas_event;
+}
+
+int
+evas_async_events_shutdown()
+{
+ if (--_init_evas_event == 0)
+ {
+ close(_fd_read);
+ close(_fd_write);
+ _fd_read = -1;
+ _fd_write = -1;
+
+ pthread_mutex_destroy(&_mutex);
+ }
+
+ return _init_evas_event;
+}
+
+EAPI int
+evas_async_events_fd_get()
+{
+ return _fd_read;
+}
+
+EAPI int
+evas_async_events_process()
+{
+ Evas_Event_Async current;
+ int check;
+ int count = 0;
+
+ do
+ {
+ check = read(_fd_read, ¤t, sizeof(current));
+
+ if (check == sizeof(current))
+ {
+ evas_object_event_callback_call(current.obj, current.type, current.event_info);
+ ++count;
+ }
+ }
+ while (check == sizeof(current));
+
+ return count;
+}
+
+EAPI Evas_Bool
+evas_async_events_put(Evas_Object *obj, Evas_Callback_Type type, void *event_info)
+{
+ Evas_Event_Async new;
+ Evas_Bool result;
+
+ result = 0;
+
+ new.obj = obj;
+ new.type = type;
+ new.event_info = event_info;
+
+ pthread_mutex_lock(&_mutex);
+ if (_fd_write != -1)
+ {
+ ssize_t check;
+ int offset = 0;
+
+ do {
+ check = write(_fd_write, &new + offset, sizeof(new) - offset);
+ offset += check;
+ } while (offset != sizeof(new) && (errno == EINTR || errno == EAGAIN));
+
+ if (offset == sizeof(new))
+ result = 1;
+ }
+ pthread_mutex_unlock(&_mutex);
+
+ return result;
+}
+
diff --git a/src/lib/canvas/evas_main.c b/src/lib/canvas/evas_main.c
index 7313a33..ca1b8dc 100644
--- a/src/lib/canvas/evas_main.c
+++ b/src/lib/canvas/evas_main.c
@@ -7,8 +7,12 @@ static int initcount = 0;
EAPI int
evas_init(void)
{
+ if (evas_async_events_init() == 0)
+ return 0;
+
if (initcount == 0)
evas_module_init();
+
return ++initcount;
}
@@ -22,6 +26,7 @@ evas_shutdown(void)
evas_common_shutdown();
evas_module_shutdown();
}
+ evas_async_events_shutdown();
return initcount;
}
diff --git a/src/lib/include/evas_private.h b/src/lib/include/evas_private.h
index 5927d25..f8fcc2b 100644
--- a/src/lib/include/evas_private.h
+++ b/src/lib/include/evas_private.h
@@ -795,6 +795,9 @@ void evas_module_use(Evas_Module *em);
void evas_module_clean(void);
void evas_module_shutdown(void);
+int evas_async_events_init();
+int evas_async_events_shutdown();
+
void _evas_walk(Evas *e);
void _evas_unwalk(Evas *e);
-------------------------------------------------------------------------
This SF.net email is sponsored by the 2008 JavaOne(SM) Conference
Register now and save $200. Hurry, offer ends at 11:59 p.m.,
Monday, April 7! Use priority code J8TLD2.
http://ad.doubleclick.net/clk;198757673;13503038;p?http://java.sun.com/javaone
_______________________________________________
enlightenment-devel mailing list
enlightenment-devel@lists.sourceforge.net
https://lists.sourceforge.net/lists/listinfo/enlightenment-devel