raster pushed a commit to branch master.

http://git.enlightenment.org/core/efl.git/commit/?id=25983dceddeda7d07220e97e227cd4c814707039

commit 25983dceddeda7d07220e97e227cd4c814707039
Author: Carsten Haitzler (Rasterman) <ras...@rasterman.com>
Date:   Tue Jun 2 20:39:57 2015 +0900

    evas render2 work - begin to make rectangles deal with render 2 basic
    infra
---
 src/lib/evas/canvas/evas_canvas.eo                 |  16 ++
 src/lib/evas/canvas/evas_object_rectangle.c        |  79 +++++-
 src/lib/evas/canvas/evas_object_smart.c            |   2 -
 src/lib/evas/canvas/evas_render.c                  |  11 +
 src/lib/evas/canvas/render2/evas_render2.c         |  80 ++++---
 src/lib/evas/canvas/render2/evas_render2.h         |   3 +-
 src/lib/evas/canvas/render2/evas_render2_th_main.c | 265 +++++++++++++++++++++
 src/lib/evas/include/evas_private.h                |   9 +
 src/modules/ecore_evas/engines/x/ecore_evas_x.c    |  43 +++-
 9 files changed, 462 insertions(+), 46 deletions(-)

diff --git a/src/lib/evas/canvas/evas_canvas.eo 
b/src/lib/evas/canvas/evas_canvas.eo
index d6dc105..79462c7 100644
--- a/src/lib/evas/canvas/evas_canvas.eo
+++ b/src/lib/evas/canvas/evas_canvas.eo
@@ -892,6 +892,22 @@ class Evas.Canvas (Eo.Base, Evas.Common_Interface)
 
          return: bool;
       }
+      render2_updates {
+         /*@
+         Render the given Evas canvas using the new rendering infra.
+
+         This is experimental and will change over time until noted here.
+
+         @return A newly allocated list of updated rectangles of thecanvas
+         (@c Eina.Rectangle structs). Free this list with
+         evas_render_updates_free().
+
+         @ingroup Evas_Canvas
+         @since 1.15 */
+
+         return: free(own(list<Eina.Rectangle *> *), evas_render_updates_free)
+            @warn_unused;
+      }
       focus_out {
          /*@
          Inform to the evas that it lost the focus.
diff --git a/src/lib/evas/canvas/evas_object_rectangle.c 
b/src/lib/evas/canvas/evas_object_rectangle.c
index cdee4ad..8f603e6 100644
--- a/src/lib/evas/canvas/evas_object_rectangle.c
+++ b/src/lib/evas/canvas/evas_object_rectangle.c
@@ -41,6 +41,13 @@ static int evas_object_rectangle_was_opaque(Evas_Object 
*eo_obj,
                                            Evas_Object_Protected_Data *obj,
                                            void *type_private_data);
 
+static void evas_object_rectangle_render2_walk(Evas_Object *eo_obj,
+                                               Evas_Object_Protected_Data *obj,
+                                               void *type_private_data,
+                                               void *updates,
+                                               int offx,
+                                               int offy);
+
 #if 0 /* usless calls for a rect object. much more useful for images etc. */
 static void evas_object_rectangle_store(Evas_Object *eo_obj);
 static void evas_object_rectangle_unstore(Evas_Object *eo_obj);
@@ -73,7 +80,8 @@ static const Evas_Object_Func object_func =
      NULL,
      NULL,
      NULL,
-     NULL
+     NULL,
+     evas_object_rectangle_render2_walk
 };
 
 /* the actual api call to add a rect */
@@ -117,6 +125,75 @@ evas_object_rectangle_init(Evas_Object *eo_obj)
 }
 
 static void
+evas_object_rectangle_render2_walk(Evas_Object *eo_obj,
+                                   Evas_Object_Protected_Data *obj,
+                                   void *type_private_data EINA_UNUSED,
+                                   void *updates, int offx, int offy)
+{
+   Eina_Bool visible_is, visible_was;
+   unsigned int col_prev, col_cur;
+
+   if (obj->clip.clipees) return;
+   visible_is = evas_object_is_visible(eo_obj, obj);
+   if (!obj->changed) goto nochange;
+
+   if ((obj->cur->clipper) && (obj->cur->cache.clip.dirty))
+     evas_object_clip_recalc(obj->cur->clipper);
+   visible_was = evas_object_was_visible(eo_obj,obj);
+   // just became visible or invisible
+   if (visible_is != visible_was)
+     {
+        printf("       UP1 %p - %i %i %ix%i\n", eo_obj,
+               obj->cur->cache.clip.x, obj->cur->cache.clip.y,
+               obj->cur->cache.clip.w, obj->cur->cache.clip.h);
+        evas_common_tilebuf_add_redraw
+          (updates,
+           obj->cur->cache.clip.x - offx, obj->cur->cache.clip.y - offy,
+           obj->cur->cache.clip.w,        obj->cur->cache.clip.h);
+        return;
+     }
+   // general change (prev and cur clip geom change)
+   col_prev = (obj->prev->color.a << 24) | (obj->prev->color.r << 16) |
+              (obj->prev->color.g << 8)  | (obj->prev->color.b      );
+   col_cur  = (obj->cur->color.a << 24)  | (obj->cur->color.r << 16) |
+              (obj->cur->color.g << 8)   | (obj->cur->color.b      );
+   if ((col_prev != col_cur) ||
+       ((obj->cur->cache.clip.x != obj->prev->cache.clip.x) ||
+        (obj->cur->cache.clip.y != obj->prev->cache.clip.y) ||
+        (obj->cur->cache.clip.w != obj->prev->cache.clip.w) ||
+        (obj->cur->cache.clip.h != obj->prev->cache.clip.h)) ||
+       (obj->cur->render_op != obj->prev->render_op) ||
+       (obj->restack)
+      )
+     {
+        printf("       UP2 %p - %i %i %ix%i\n", eo_obj,
+               obj->prev->cache.clip.x, obj->prev->cache.clip.y,
+               obj->prev->cache.clip.w, obj->prev->cache.clip.h);
+        evas_common_tilebuf_add_redraw
+          (updates,
+           obj->prev->cache.clip.x - offx, obj->prev->cache.clip.y - offy,
+           obj->prev->cache.clip.w,        obj->prev->cache.clip.h);
+        evas_common_tilebuf_add_redraw
+          (updates,
+           obj->cur->cache.clip.x - offx, obj->cur->cache.clip.y - offy,
+           obj->cur->cache.clip.w,        obj->cur->cache.clip.h);
+        return;
+     }
+nochange:
+   // object hasn't really changed
+   if ((visible_is) && (evas_object_is_opaque(eo_obj, obj)))
+     {
+        printf("       NO- %p - %i %i %ix%i\n", eo_obj,
+               obj->cur->cache.clip.x, obj->cur->cache.clip.y,
+               obj->cur->cache.clip.w, obj->cur->cache.clip.h);
+        evas_common_tilebuf_del_redraw
+          (updates,
+           obj->cur->cache.clip.x - offx, obj->cur->cache.clip.y - offy,
+           obj->cur->cache.clip.w,        obj->cur->cache.clip.h);
+     }
+}
+
+static void
 evas_object_rectangle_render(Evas_Object *eo_obj EINA_UNUSED,
                             Evas_Object_Protected_Data *obj,
                             void *type_private_data EINA_UNUSED,
diff --git a/src/lib/evas/canvas/evas_object_smart.c 
b/src/lib/evas/canvas/evas_object_smart.c
index 3aeb937..b5ced9e 100644
--- a/src/lib/evas/canvas/evas_object_smart.c
+++ b/src/lib/evas/canvas/evas_object_smart.c
@@ -434,7 +434,6 @@ _evas_object_smart_members_get(Eo *eo_obj, Evas_Smart_Data 
*o)
    Eina_List *members = NULL;
    Eina_Inlist *member;
 
-   evas_object_async_block(obj);
    for (member = o->contained; member; member = member->next)
      members = eina_list_append(members, ((Evas_Object_Protected_Data 
*)member)->object);
 
@@ -448,7 +447,6 @@ evas_object_smart_members_get_direct(const Evas_Object 
*eo_obj)
    MAGIC_CHECK(eo_obj, Evas_Object, MAGIC_OBJ);
    return NULL;
    MAGIC_CHECK_END();
-   evas_object_async_block(obj);
    if (!eo_isa(eo_obj, MY_CLASS)) return NULL;
    Evas_Smart_Data *o = eo_data_scope_get(eo_obj, MY_CLASS);
    return o->contained;
diff --git a/src/lib/evas/canvas/evas_render.c 
b/src/lib/evas/canvas/evas_render.c
index 0625f35..b97552c 100644
--- a/src/lib/evas/canvas/evas_render.c
+++ b/src/lib/evas/canvas/evas_render.c
@@ -2818,6 +2818,17 @@ _evas_canvas_render2(Eo *eo_e, Evas_Public_Data *e)
    return ret;
 }
 
+EOLIAN Eina_List *
+_evas_canvas_render2_updates(Eo *eo_e, Evas_Public_Data *e)
+{
+   Eina_List *updates = NULL;
+
+   eina_evlog("+render2_updates", eo_e, 0.0, NULL);
+   updates = _evas_render2_updates(eo_e, e);
+   eina_evlog("-render2_updates", eo_e, 0.0, NULL);
+   return updates;
+}
+
 EOLIAN Eina_Bool
 _evas_canvas_render_async(Eo *eo_e, Evas_Public_Data *e)
 {
diff --git a/src/lib/evas/canvas/render2/evas_render2.c 
b/src/lib/evas/canvas/render2/evas_render2.c
index b4080e4..803101b 100644
--- a/src/lib/evas/canvas/render2/evas_render2.c
+++ b/src/lib/evas/canvas/render2/evas_render2.c
@@ -1,6 +1,5 @@
 #include "evas_render2.h"
 
-#ifdef EVAS_RENDER_DEBUG_TIMING
 #include <sys/time.h>
 
 #ifndef _WIN32
@@ -23,12 +22,8 @@ static inline void
 out_time(double t)
 {
    double b = (t * 100.0) / (1.0 / 60.0);
-   printf("%1.8fs (%1.2f%% 60fps budget)\n", t, b);
+   printf("%1.2f%% / 60fps\n", b);
 }
-#endif
-
-// a list of canvases currently rendering
-static Eina_List *_rendering = NULL;
 
 static void
 _always_call(Eo *eo_e, Evas_Callback_Type type, void *event_info)
@@ -41,10 +36,31 @@ _always_call(Eo *eo_e, Evas_Callback_Type type, void 
*event_info)
    for (i = 0; i < freeze_num; i++) eo_do(eo_e, eo_event_freeze());
 }
 
+// a list of canvases currently rendering
+static Eina_List *_rendering = NULL;
+
+// just put the thread code inlined here for now as opposed to separate files
+#include "evas_render2_th_main.c"
+
+// init all relevant render threads if needed
+static void
+_evas_render2_th_init(void)
+{
+   static Eina_Bool initted = EINA_FALSE;
+
+   if (initted) return;
+   initted = EINA_TRUE;
+   _th_main_queue = eina_thread_queue_new();
+   if (!eina_thread_create(&_th_main, EINA_THREAD_URGENT, 0,
+                           _evas_render2_th_main, NULL))
+     ERR("Cannot create render2 thread");
+}
 
 Eina_Bool
 _evas_render2(Eo *eo_e, Evas_Public_Data *e)
 {
+   double t;
+
    // if nothing changed at all since last render - skip this frame
    if (!e->changed) return EINA_FALSE;
    // we are still rendering while being asked to render - skip this
@@ -55,61 +71,61 @@ _evas_render2(Eo *eo_e, Evas_Public_Data *e)
    if ((e->output.w != e->viewport.w) || (e->output.h != e->viewport.h))
      ERR("viewport size != output size!");
 
+   // if render threads not initted - init them - maybe move this later?
+   _evas_render2_th_init();
+
+   printf("------------------------------------------------ %p %p\n", eo_e, e);
    // wait for any previous render pass to do its thing
+   t = get_time();
    evas_canvas_async_block(e);
+   t = get_time() - t;
+   printf("T: block wait: "); out_time(t);
    // we have to calculate smare objects before render so do that here
+   t = get_time();
    evas_call_smarts_calculate(eo_e);
+   t = get_time() - t;
+   printf("T: smart calc: "); out_time(t);
    // call canvas callbacks saying we are in the pre-render state
    _always_call(eo_e, EVAS_CALLBACK_RENDER_PRE, NULL);
    // bock any susbequent rneders from doing this walk
    eina_lock_take(&(e->lock_objects));
-   // XXX: gain a reference
+   // gain a reference
    eo_ref(eo_e);
-   // XXX: put into the "i'm rendering" pool
+   // put into the "i'm rendering" pool
    e->rendering = EINA_TRUE;
    _rendering = eina_list_append(_rendering, eo_e);
-   // XXX; should wake up thread here to begin doing it's work
-
 
-
-   // XXX: call this from object walk thread
-   eina_lock_release(&(e->lock_objects));
-   // XXX: remove from the "i'm rendering" pool - do back in mainloop
-   e->rendering = EINA_FALSE;
-   _rendering = eina_list_remove(_rendering, eo_e);
-
-
-
-   // XXX: like below - call from thread messages - figure out if they just
-   // should be dumbly called before render post anyway
+   // call our flush pre at this point before rendering begins...
    _always_call(eo_e, EVAS_CALLBACK_RENDER_FLUSH_PRE, NULL);
-   _always_call(eo_e, EVAS_CALLBACK_RENDER_FLUSH_POST, NULL);
-   // XXX: call render post - should be a result from thread message called
-   // from mainloop - also fill in post struct
-   Evas_Event_Render_Post post;
-   _always_call(eo_e, EVAS_CALLBACK_RENDER_POST, &post);
 
-   // XXX: release our reference
-   eo_unref(eo_e);
+   // tell main render thread to wake up and begin processing this canvas
+   _evas_render2_th_main_msg_render(eo_e, e);
 
-   printf("%p %p\n", eo_e, e);
    return EINA_FALSE;
 }
 
-void
-_evas_norender2(Eo *eo_e EINA_UNUSED, Evas_Public_Data *e)
+Eina_List *
+_evas_render2_updates(Eo *eo_e, Evas_Public_Data *e)
 {
-   evas_canvas_async_block(e);
+   if (!_evas_render2(eo_e, e)) return NULL;
+   return _evas_render2_updates_wait(eo_e, e);
 }
 
 Eina_List *
 _evas_render2_updates_wait(Eo *eo_e EINA_UNUSED, Evas_Public_Data *e)
 {
    evas_canvas_async_block(e);
+   while (e->rendering) evas_async_events_process_blocking();
    return NULL;
 }
 
 void
+_evas_norender2(Eo *eo_e EINA_UNUSED, Evas_Public_Data *e)
+{
+   evas_canvas_async_block(e);
+}
+
+void
 _evas_render2_idle_flush(Eo *eo_e EINA_UNUSED, Evas_Public_Data *e)
 {
    evas_canvas_async_block(e);
diff --git a/src/lib/evas/canvas/render2/evas_render2.h 
b/src/lib/evas/canvas/render2/evas_render2.h
index 95982dc..bdad709 100644
--- a/src/lib/evas/canvas/render2/evas_render2.h
+++ b/src/lib/evas/canvas/render2/evas_render2.h
@@ -9,8 +9,9 @@
 #endif
 
 Eina_Bool  _evas_render2(Eo *eo_e, Evas_Public_Data *e);
-void       _evas_norender2(Eo *eo_e, Evas_Public_Data *e);
+Eina_List *_evas_render2_updates(Eo *eo_e, Evas_Public_Data *e);
 Eina_List *_evas_render2_updates_wait(Eo *eo_e, Evas_Public_Data *e);
+void       _evas_norender2(Eo *eo_e, Evas_Public_Data *e);
 void       _evas_render2_idle_flush(Eo *eo_e, Evas_Public_Data *e);
 void       _evas_render2_sync(Eo *eo_e, Evas_Public_Data *e);
 void       _evas_render2_dump(Eo *eo_e, Evas_Public_Data *e);
diff --git a/src/lib/evas/canvas/render2/evas_render2_th_main.c 
b/src/lib/evas/canvas/render2/evas_render2_th_main.c
new file mode 100644
index 0000000..c462d87
--- /dev/null
+++ b/src/lib/evas/canvas/render2/evas_render2_th_main.c
@@ -0,0 +1,265 @@
+//#define DBG_OBJTREE 1
+
+#define OBJ_ARRAY_PUSH(array, obj)     \
+   do                                  \
+   {                                   \
+      eina_array_push(array, obj);     \
+      eo_data_ref(obj->object, NULL);  \
+   } while (0)
+
+#define OBJS_ARRAY_CLEAN(array)                          \
+   do                                                    \
+   {                                                     \
+      Evas_Object_Protected_Data *item;                  \
+      Eina_Array_Iterator iterator;                      \
+      unsigned int idx;                                  \
+      EINA_ARRAY_ITER_NEXT(array, idx, item, iterator)   \
+      eo_data_unref(item->object, item);                 \
+      eina_array_clean(array);                           \
+   } while (0)
+
+typedef struct _Msg_Main_Render Msg_Main_Render;
+typedef struct _Render2_Finish_Data Render2_Finish_Data;
+
+struct _Msg_Main_Render
+{
+   Eina_Thread_Queue_Msg  head;
+   Eo                    *eo_e;
+   Evas_Public_Data      *e;
+};
+
+struct _Render2_Finish_Data
+{
+   Eo                    *eo_e;
+   Evas_Public_Data      *e;
+   Eina_List             *updates;
+};
+
+static Eina_Thread_Queue *_th_main_queue = NULL;
+static Eina_Thread _th_main;
+
+#ifdef DBG_OBJTREE
+static void
+indent(int l)
+{
+   int i; for (i = 0; i < l; i++) printf(" ");
+}
+#endif
+
+static void
+_evas_render2_th_main_delete_objects_clean(Evas_Public_Data *e)
+{
+   Evas_Object_Protected_Data *obj;
+   unsigned int i;
+   double t;
+
+   // cleanup deferred object deletion
+   t = get_time();
+   for (i = 0; i < e->delete_objects.count; ++i)
+     {
+        obj = eina_array_data_get(&e->delete_objects, i);
+        evas_object_free(obj->object, 1);
+     }
+//   OBJS_ARRAY_CLEAN(&e->delete_objects);
+   eina_array_clean(&e->delete_objects);
+   t = get_time() - t;
+   printf("T: object deletion: "); out_time(t);
+}
+
+static void
+_evas_render2_th_main_mainloop_done(void *data, Evas_Callback_Type type 
EINA_UNUSED, void *event_info EINA_UNUSED)
+{
+   Render2_Finish_Data *render_finish_data = data;
+   Evas_Event_Render_Post post;
+   Eo *eo_e;
+   Evas_Public_Data *e;
+   Eina_Rectangle *rect;
+
+   e = render_finish_data->e;
+   eo_e = render_finish_data->eo_e;
+   // call the flush post callbacks
+   _always_call(render_finish_data->eo_e, EVAS_CALLBACK_RENDER_FLUSH_POST, 
NULL);
+
+   // and now call the actual render post callbacks with updates list
+   post.updated_area = render_finish_data->updates;
+   _always_call(eo_e, EVAS_CALLBACK_RENDER_POST, &post);
+
+   EINA_LIST_FREE(render_finish_data->updates, rect) free(rect);
+   free(render_finish_data);
+   _evas_render2_th_main_delete_objects_clean(e);
+}
+
+static Eina_Bool
+_evas_render2_th_main_obj_del_handle(Evas_Public_Data *e,
+                                     Evas_Object_Protected_Data *obj)
+{
+   if (obj->delete_me == 2)
+     {
+        OBJ_ARRAY_PUSH(&e->delete_objects, obj);
+        obj->delete_me++;
+        return EINA_FALSE;
+     }
+   else if (obj->delete_me != 0) obj->delete_me++;
+   return EINA_TRUE;
+}
+
+static void
+_evas_render2_th_main_obj_basic_process(Evas_Public_Data *e,
+                                        Evas_Object_Protected_Data *obj,
+                                        void *updates,
+                                        int offx,
+                                        int offy,
+                                        int l EINA_UNUSED)
+{
+   Evas_Object *eo_obj = obj->object;
+
+   if (!_evas_render2_th_main_obj_del_handle(e, obj)) return;
+   evas_object_clip_recalc(obj);
+#ifdef DBG_OBJTREE
+   indent(l); printf("BASIC %p %p [%10s]\n", e, eo_obj, obj->type);
+#endif
+   if (obj->func->render2_walk)
+     obj->func->render2_walk(eo_obj, obj, obj->private_data,
+                             updates, offx, offy);
+   if (obj->changed)
+     {
+        evas_object_clip_changes_clean(eo_obj);
+        evas_object_cur_prev(eo_obj);
+        evas_object_change_reset(eo_obj);
+     }
+}
+
+static void
+_evas_render2_th_main_obj_process(Evas_Public_Data *e,
+                                  Evas_Object_Protected_Data *obj,
+                                  void *updates,
+                                  int offx,
+                                  int offy,
+                                  int l EINA_UNUSED)
+{
+   // process object OR walk through child objects if smart and process those
+   Evas_Object_Protected_Data *obj2;
+   Evas_Object *eo_obj = obj->object;
+   const Eina_Inlist *il;
+
+   if (!obj->changed) return;
+   il = evas_object_smart_members_get_direct(eo_obj);
+   if (il)
+     {
+        if (!_evas_render2_th_main_obj_del_handle(e, obj)) return;
+        evas_object_clip_recalc(obj);
+#ifdef DBG_OBJTREE
+        indent(l); printf("SMART %p %p [%10s] ch %i\n", e, eo_obj, obj->type, 
obj->changed);
+#endif
+        if (obj->func->render2_walk)
+          obj->func->render2_walk(eo_obj, obj, obj->private_data,
+                                  updates, offx, offy);
+        EINA_INLIST_FOREACH(il, obj2)
+          _evas_render2_th_main_obj_process(e, obj2, updates,
+                                            offx, offy, l + 1);
+        if (obj->changed)
+          {
+             evas_object_clip_changes_clean(eo_obj);
+             evas_object_cur_prev(eo_obj);
+             evas_object_change_reset(eo_obj);
+          }
+     }
+   else _evas_render2_th_main_obj_basic_process(e, obj, updates,
+                                                offx, offy, l);
+}
+
+static void
+_evas_render2_th_main_do(Eo *eo_e, Evas_Public_Data *e)
+{
+   Render2_Finish_Data *render_finish_data;
+   Evas_Layer *lay;
+   Evas_Object_Protected_Data *obj;
+   double t;
+   Tilebuf *updates = NULL;
+   Tilebuf_Rect *rects, *r;
+   Eina_List *updates_list = NULL;
+   Eina_Rectangle *rect;
+
+   updates = evas_common_tilebuf_new(e->output.w, e->output.h);
+   evas_common_tilebuf_set_tile_size(updates, TILESIZE, TILESIZE);
+//   evas_common_tilebuf_tile_strict_set(updates, EINA_TRUE);
+   static int num = 0;
+   printf("........... updates # %i\n", num++);
+   t = get_time();
+   EINA_INLIST_FOREACH(e->layers, lay)
+     {
+        EINA_INLIST_FOREACH(lay->objects, obj)
+          {
+             _evas_render2_th_main_obj_process(e, obj,
+                                               updates, 0, 0,
+                                               0);
+          }
+     }
+   t = get_time() - t;
+   printf("T: update generation: "); out_time(t);
+
+   rects = evas_common_tilebuf_get_render_rects(updates);
+   EINA_INLIST_FOREACH(EINA_INLIST_GET(rects), r)
+     {
+        rect = malloc(sizeof(Eina_Rectangle));
+        if (rect)
+          {
+             printf(" %i %i %ix%i\n", r->x, r->y, r->w, r->h);
+             rect->x = r->x; rect->y = r->y;
+             rect->w = r->w; rect->h = r->h;
+             updates_list = eina_list_append(updates_list, rect);
+          }
+     }
+   evas_common_tilebuf_free_render_rects(rects);
+
+   evas_common_tilebuf_free(updates);
+
+   e->changed = EINA_FALSE;
+   // remove from the "i'm rendering" pool - do back in mainloop
+   e->rendering = EINA_FALSE;
+   _rendering = eina_list_remove(_rendering, eo_e);
+   // unblock mainlopp that may be waiting on the render thread
+   eina_lock_release(&(e->lock_objects));
+
+   // send back 
+   render_finish_data = calloc(1, sizeof(Render2_Finish_Data));
+   if (render_finish_data)
+     {
+        render_finish_data->eo_e = eo_e;
+        render_finish_data->e = e;
+        render_finish_data->updates = updates_list;
+        evas_async_events_put(render_finish_data, 0, NULL,
+                              _evas_render2_th_main_mainloop_done);
+     }
+   else
+     {
+        EINA_LIST_FREE(updates_list, rect) free(rect);
+     }
+   eo_unref(eo_e);
+}
+
+static void *
+_evas_render2_th_main(void *data EINA_UNUSED, Eina_Thread thread EINA_UNUSED)
+{
+   void *ref = NULL;
+   Msg_Main_Render *msg;
+
+   for (;;)
+     {
+        msg = eina_thread_queue_wait(_th_main_queue, &ref);
+        _evas_render2_th_main_do(msg->eo_e, msg->e);
+        eina_thread_queue_wait_done(_th_main_queue, ref);
+     }
+   return NULL;
+}
+
+static void
+_evas_render2_th_main_msg_render(Eo *eo_e, Evas_Public_Data *e)
+{
+   void *ref;
+   Msg_Main_Render *msg =
+     eina_thread_queue_send(_th_main_queue, sizeof(Msg_Main_Render), &ref);
+   msg->eo_e = eo_e;
+   msg->e = e;
+   eina_thread_queue_send_done(_th_main_queue, ref);
+}
diff --git a/src/lib/evas/include/evas_private.h 
b/src/lib/evas/include/evas_private.h
index 52feb58..b2678df 100644
--- a/src/lib/evas/include/evas_private.h
+++ b/src/lib/evas/include/evas_private.h
@@ -1216,6 +1216,15 @@ struct _Evas_Object_Func
                            Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, 
Evas_Coord *h);
 
    int (*can_map) (Evas_Object *obj);
+
+// new render2 functions
+
+   void (*render2_walk) (Evas_Object *obj, Evas_Object_Protected_Data *pd,
+                         void *type_private_data, void *updates,
+                         int offx, int offy);
+//   void (*render2) (Evas_Object *obj, Evas_Object_Protected_Data *pd,
+//                    void *type_private_data, void *output, void *context,
+//                    void *surface, int x, int y);
 };
 
 struct _Evas_Func
diff --git a/src/modules/ecore_evas/engines/x/ecore_evas_x.c 
b/src/modules/ecore_evas/engines/x/ecore_evas_x.c
index 63ccfbc..a090da7 100644
--- a/src/modules/ecore_evas/engines/x/ecore_evas_x.c
+++ b/src/modules/ecore_evas/engines/x/ecore_evas_x.c
@@ -759,6 +759,7 @@ _ecore_evas_x_render(Ecore_Evas *ee)
    Eina_List *ll;
    Ecore_Evas *ee2;
    Ecore_Evas_Engine_Data_X11 *edata = ee->engine.data;
+   static int render2 = -1;
 
    if ((!ee->no_comp_sync) && (_ecore_evas_app_comp_sync) &&
        (edata->sync_counter) && (!edata->sync_began) &&
@@ -780,20 +781,42 @@ _ecore_evas_x_render(Ecore_Evas *ee)
      }
 
    if (ee->func.fn_pre_render) ee->func.fn_pre_render(ee);
-   if (!ee->can_async_render)
+   if (render2 == -1)
      {
-        Eina_List *updates = evas_render_updates(ee->evas);
-        rend = _render_updates_process(ee, updates);
-        evas_render_updates_free(updates);
+        if (getenv("RENDER2")) render2 = 1;
+        else render2 = 0;
      }
-   else if (evas_render_async(ee->evas))
+   if (render2)
      {
-        EDBG("ee=%p started asynchronous render.", ee);
-        ee->in_async_render = EINA_TRUE;
-        rend = 1;
+        if (!ee->can_async_render)
+          {
+             Eina_List *updates = evas_render2_updates(ee->evas);
+             rend = _render_updates_process(ee, updates);
+             evas_render_updates_free(updates);
+          }
+        else
+          {
+             ee->in_async_render = EINA_TRUE;
+             if (evas_render2(ee->evas)) rend = 1;
+             else ee->in_async_render = EINA_FALSE;
+          }
+     }
+   else
+     {
+        if (!ee->can_async_render)
+          {
+             Eina_List *updates = evas_render_updates(ee->evas);
+             rend = _render_updates_process(ee, updates);
+             evas_render_updates_free(updates);
+          }
+        else if (evas_render_async(ee->evas))
+          {
+             EDBG("ee=%p started asynchronous render.", ee);
+             ee->in_async_render = EINA_TRUE;
+             rend = 1;
+          }
+        else if (ee->func.fn_post_render) ee->func.fn_post_render(ee);
      }
-   else if (ee->func.fn_post_render) ee->func.fn_post_render(ee);
-
    return rend;
 }
 

-- 


Reply via email to