the start of other objects being able to map! text objects work.. tested.
authorraster <raster@7cbeb6ba-43b4-40fd-8cce-4c39aea84d33>
Wed, 28 Oct 2009 08:59:01 +0000 (08:59 +0000)
committerraster <raster@7cbeb6ba-43b4-40fd-8cce-4c39aea84d33>
Wed, 28 Oct 2009 08:59:01 +0000 (08:59 +0000)
git-svn-id: svn+ssh://svn.enlightenment.org/var/svn/e/trunk/evas@43323 7cbeb6ba-43b4-40fd-8cce-4c39aea84d33

22 files changed:
src/lib/Evas.h
src/lib/canvas/evas_map.c
src/lib/canvas/evas_object_gradient.c
src/lib/canvas/evas_object_gradient2_linear.c
src/lib/canvas/evas_object_gradient2_radial.c
src/lib/canvas/evas_object_image.c
src/lib/canvas/evas_object_line.c
src/lib/canvas/evas_object_main.c
src/lib/canvas/evas_object_polygon.c
src/lib/canvas/evas_object_rectangle.c
src/lib/canvas/evas_object_smart.c
src/lib/canvas/evas_object_textblock.c
src/lib/canvas/evas_render.c
src/lib/include/evas_private.h
src/modules/engines/cairo_x11/evas_engine.c
src/modules/engines/direct3d/evas_engine.c
src/modules/engines/directfb/evas_engine.c
src/modules/engines/gl_x11/evas_engine.c
src/modules/engines/quartz/evas_engine.c
src/modules/engines/software_16/evas_engine.c
src/modules/engines/software_generic/evas_engine.c
src/modules/engines/xrender_x11/evas_engine.c

index e2e3ec5..05dd2b7 100644 (file)
@@ -857,13 +857,13 @@ extern "C" {
    EAPI void              evas_map_util_rotate              (Evas_Map *m, double degrees, Evas_Coord cx, Evas_Coord cy);
    EAPI void              evas_map_util_zoom                (Evas_Map *m, double zoomx, double zoomy, Evas_Coord cx, Evas_Coord cy);
 
-   EAPI Evas_Map         *evas_map_new                      (unsigned long count);
+   EAPI Evas_Map         *evas_map_new                      (int count);
    EAPI Evas_Map         *evas_map_dup                      (const Evas_Map *m);
    EAPI void              evas_map_free                     (Evas_Map *m);
-   EAPI void              evas_map_point_coord_set          (Evas_Map *m, unsigned long idx, Evas_Coord x, Evas_Coord y, Evas_Coord z);
-   EAPI void              evas_map_point_coord_get          (const Evas_Map *m, unsigned long idx, Evas_Coord *x, Evas_Coord *y, Evas_Coord *z);
-   EAPI void              evas_map_point_image_uv_set       (Evas_Map *m, unsigned long idx, double u, double v);
-   EAPI void              evas_map_point_image_uv_get       (const Evas_Map *m, unsigned long idx, double *u, double *v);
+   EAPI void              evas_map_point_coord_set          (Evas_Map *m, int idx, Evas_Coord x, Evas_Coord y, Evas_Coord z);
+   EAPI void              evas_map_point_coord_get          (const Evas_Map *m, int idx, Evas_Coord *x, Evas_Coord *y, Evas_Coord *z);
+   EAPI void              evas_map_point_image_uv_set       (Evas_Map *m, int idx, double u, double v);
+   EAPI void              evas_map_point_image_uv_get       (const Evas_Map *m, int idx, double *u, double *v);
 
 /* smart objects */
    EINA_DEPRECATED EAPI Evas_Smart *evas_smart_new          (const char *name, void (*func_add) (Evas_Object *obj), void (*func_del) (Evas_Object *obj), void (*func_layer_set) (Evas_Object *obj, int l), void (*func_raise) (Evas_Object *obj), void (*func_lower) (Evas_Object *obj), void (*func_stack_above) (Evas_Object *obj, Evas_Object *above), void (*func_stack_below) (Evas_Object *obj, Evas_Object *below), void (*func_move) (Evas_Object *obj, Evas_Coord x, Evas_Coord y), void (*func_resize) (Evas_Object *obj, Evas_Coord w, Evas_Coord h), void (*func_show) (Evas_Object *obj), void (*func_hide) (Evas_Object *obj), void (*func_color_set) (Evas_Object *obj, int r, int g, int b, int a), void (*func_clip_set) (Evas_Object *obj, Evas_Object *clip), void (*func_clip_unset) (Evas_Object *obj), const void *data) EINA_WARN_UNUSED_RESULT EINA_ARG_NONNULL(1) EINA_MALLOC;
index 8f792a4..22f5634 100644 (file)
@@ -3,31 +3,10 @@
 #include <math.h>
 
 static void
-_calc_map_geometry(Evas_Object *obj)
+_evas_map_calc_geom_change(Evas_Object *obj)
 {
    int is, was = 0, pass = 0;
-   Evas_Coord x1, x2, y1, y2;
-   const Evas_Map_Point *p, *p_end;
 
-   if (!obj->cur.map) return;
-   p = obj->cur.map->points;
-   p_end = p + 4;
-   x1 = p->x;
-   x2 = p->x;
-   y1 = p->y;
-   y2 = p->y;
-   p++;
-   for (; p < p_end; p++)
-     {
-        if (p->x < x1) x1 = p->x;
-        if (p->x > x2) x2 = p->x;
-        if (p->y < y1) y1 = p->y;
-        if (p->y > y2) y2 = p->y;
-     }
-   obj->cur.geometry.x = x1;
-   obj->cur.geometry.y = y1;
-   obj->cur.geometry.w = (x2 - x1) + 1;
-   obj->cur.geometry.h = (y2 - y1) + 1;
    evas_object_change(obj);
    evas_object_clip_dirty(obj);
    if (obj->layer->evas->events_frozen <= 0)
@@ -53,32 +32,39 @@ _calc_map_geometry(Evas_Object *obj)
    evas_object_inform_call_resize(obj);
 }
 
-EAPI void
-evas_object_map_enable_set(Evas_Object *obj, Eina_Bool enabled)
+static void
+_evas_map_calc_map_geometry(Evas_Object *obj)
 {
-   MAGIC_CHECK(obj, Evas_Object, MAGIC_OBJ);
-   return;
-   MAGIC_CHECK_END();
-   if (obj->cur.usemap == !!enabled) return;
-   obj->cur.usemap = enabled;
-   if (obj->cur.usemap) _calc_map_geometry(obj);
-}
+   Evas_Coord x1, x2, y1, y2;
+   const Evas_Map_Point *p, *p_end;
 
-EAPI Eina_Bool
-evas_object_map_enable_get(const Evas_Object *obj)
-{
-   MAGIC_CHECK(obj, Evas_Object, MAGIC_OBJ);
-   return 0;
-   MAGIC_CHECK_END();
-   return obj->cur.usemap;
+   if (!obj->cur.map) return;
+   p = obj->cur.map->points;
+   p_end = p + 4;
+   x1 = p->x;
+   x2 = p->x;
+   y1 = p->y;
+   y2 = p->y;
+   p++;
+   for (; p < p_end; p++)
+     {
+        if (p->x < x1) x1 = p->x;
+        if (p->x > x2) x2 = p->x;
+        if (p->y < y1) y1 = p->y;
+        if (p->y > y2) y2 = p->y;
+     }
+   obj->cur.geometry.x = x1;
+   obj->cur.geometry.y = y1;
+   obj->cur.geometry.w = (x2 - x1) + 1;
+   obj->cur.geometry.h = (y2 - y1) + 1;
+   _evas_map_calc_geom_change(obj);
 }
 
 static inline Evas_Map *
-_evas_map_new(unsigned long count)
+_evas_map_new(int count)
 {
-   Evas_Map *m = malloc(sizeof(Evas_Map) + count * sizeof(Evas_Map_Point));
-   if (!m)
-     return NULL;
+   Evas_Map *m = calloc(1, sizeof(Evas_Map) + count * sizeof(Evas_Map_Point));
+   if (!m) return NULL;
    m->count = count;
    return m;
 }
@@ -87,8 +73,7 @@ static inline Evas_Map *
 _evas_map_dup(const Evas_Map *orig)
 {
    Evas_Map *copy = _evas_map_new(orig->count);
-   if (!orig)
-     return NULL;
+   if (!copy) return NULL;
    memcpy(copy->points, orig->points, orig->count * sizeof(Evas_Map_Point));
    return copy;
 }
@@ -113,12 +98,99 @@ _evas_map_free(Evas_Map *m)
 }
 
 /**
- * Set current object transformation map (or unset if it's @c NULL).
+ * Enable or disable the map that is set
+ * 
+ * This enables the map that is set or disables it. On enable, the object
+ * geometry will be saved, and the new geometry will change (position and
+ * size) to reflect the map geometry set. If none is set yet, this may be
+ * an undefined geometry, unless you have already set the map with
+ * evas_object_map_set(). It is suggested you first set a map with
+ * evas_object_map_set() with valid useful coordinatesm then enable and
+ * disable the map with evas_object_map_enable_set() as needed.
+ * 
+ * @param obj object to enable the map on
+ * @param enbled enabled state
+ */
+EAPI void
+evas_object_map_enable_set(Evas_Object *obj, Eina_Bool enabled)
+{
+   MAGIC_CHECK(obj, Evas_Object, MAGIC_OBJ);
+   return;
+   MAGIC_CHECK_END();
+   if (obj->cur.usemap == !!enabled) return;
+   obj->cur.usemap = enabled;
+   if (enabled)
+     {
+        if (!obj->cur.map)
+          obj->cur.map = _evas_map_new(4);
+        obj->cur.map->normal_geometry = obj->cur.geometry;
+     }
+   else
+     {
+        if (obj->cur.map)
+          {
+             obj->cur.geometry = obj->cur.map->normal_geometry;
+             _evas_map_calc_geom_change(obj);
+          }
+     }
+   if (obj->cur.usemap) _evas_map_calc_map_geometry(obj);
+}
+
+/**
+ * Get the map enabled state
+ * 
+ * This returns the currently enabled state of the map on the object indicated.
+ * The default map enable state is off. You can enable and disable it with
+ * evas_object_map_enable_set().
+ * 
+ * @param obj object to get the map enabled state from
+ * @return the map enabled state
+ */
+EAPI Eina_Bool
+evas_object_map_enable_get(const Evas_Object *obj)
+{
+   MAGIC_CHECK(obj, Evas_Object, MAGIC_OBJ);
+   return 0;
+   MAGIC_CHECK_END();
+   return obj->cur.usemap;
+}
+
+/**
+ * Set current object transformation map.
+ * 
+ * This sets the map on a given object. It is copied from the @p map pointer,
+ * so there is no need to keep the @p map object if you don't need it anymore.
+ * 
+ * A map is a set of 4 points which have canvas x, y coordinates per point,
+ * with an optional z point value as a hint for perspective correction, if it
+ * is available. As well each point has u and v coordinates. These are like
+ * "texture coordinates" in OpenGL in that they define a point in the source
+ * image that is mapped to that map vertex/point. The u corresponds to the x
+ * coordinate of this mapped point and v, the y coordinate. Note that these
+ * coordinates describe a bounding region to sample. If you have a 200x100
+ * source image and wannt to display it at 200x100 with proper pixel
+ * precision, then do:
+ * 
+ * @code
+ * Evas_Map *m = evas_map_new(4);
+ * evas_map_point_coord_set(m, 0,   0,   0, 0);
+ * evas_map_point_coord_set(m, 1, 200,   0, 0);
+ * evas_map_point_coord_set(m, 2, 200, 100, 0);
+ * evas_map_point_coord_set(m, 3,   0, 100, 0);
+ * evas_map_point_image_uv_set(m, 0,   0,   0);
+ * evas_map_point_image_uv_set(m, 1, 200,   0);
+ * evas_map_point_image_uv_set(m, 2, 200, 100);
+ * evas_map_point_image_uv_set(m, 3,   0, 100);
+ * evas_object_map_set(obj, m);
+ * evas_map_free(m);
+ * @endcode
+ * 
+ * Note that the map points a uv coordinates match the image geometry. If
+ * the @p map parameter is NULL, the sotred map will be freed and geometry
+ * prior to enabling/setting a map will be restored.
  *
- * @param obj object to change transformation map.
- * @param map new map to use or @c NULL to unset map. This function
- *        will copy the given map, so it's safe to destroy it
- *        afterwards.
+ * @param obj object to change transformation map
+ * @param map new map to use
  *
  * @see evas_map_new()
  */
@@ -132,6 +204,7 @@ evas_object_map_set(Evas_Object *obj, const Evas_Map *map)
      {
         if (obj->cur.map)
           {
+             obj->cur.geometry = obj->cur.map->normal_geometry;
              if (!obj->prev.map)
                {
                  _evas_map_free(obj->cur.map);
@@ -139,6 +212,8 @@ evas_object_map_set(Evas_Object *obj, const Evas_Map *map)
                   return;
                }
              obj->cur.map = NULL;
+             if (!obj->cur.usemap) _evas_map_calc_geom_change(obj);
+             else _evas_map_calc_map_geometry(obj);
           }
         return;
      }
@@ -152,18 +227,28 @@ evas_object_map_set(Evas_Object *obj, const Evas_Map *map)
        _evas_map_copy(obj->cur.map, map);
         obj->prev.map = NULL;
      }
-   if (obj->cur.usemap) _calc_map_geometry(obj);
+   if (obj->cur.usemap) _evas_map_calc_map_geometry(obj);
 }
 
 /**
  * Get current object transformation map.
+ * 
+ * This returns the current internal map set on the indicated object. It is
+ * intended for read-only acces and is only valid as long as the object is
+ * not deleted or the map on the object is not changed. If you wish to modify
+ * the map and set it back do the following:
+ * 
+ * @code
+ * const Evas_Map *m = evas_object_map_get(obj);
+ * Evas_Map *m2 = evas_map_dup(m);
+ * evas_map_util_rotate(m2, 30.0, 0, 0);
+ * evas_object_map_set(obj);
+ * evas_map_free(m2);
+ * @endcode
  *
  * @param obj object to query transformation map.
- * @return map reference to map in use. This is an internal reference,
- *         don't change it anyhow. Use evas_map_dup() if you want to
- *         change it and use somewhere else, or even take reference
- *         for long time. The returned reference may go away when
- *         another map is set or object is destroyed.
+ * @return map reference to map in use. This is an internal data structure, so
+ * do not modify it.
  *
  * @see evas_object_map_set()
  */
@@ -173,20 +258,19 @@ evas_object_map_get(const Evas_Object *obj)
    MAGIC_CHECK(obj, Evas_Object, MAGIC_OBJ);
    return NULL;
    MAGIC_CHECK_END();
-   if (obj->cur.map)
-     return obj->cur.map;
-   else
-     return NULL;
+   if (obj->cur.map) return obj->cur.map;
+   return NULL;
 }
 
 /**
- * Creates map of transformation points to be later used with an evas object.
- *
- * @param count number of points in the map. So far it @b must be 4 as
- *        evas will use that exact number. The parameter is for
- *        extensibility. Giving any value other than 4 will return @c NULL.
+ * Create map of transformation points to be later used with an evas object.
  *
- * @return a newly allocated map or @c NULL on errors.
+ * This creates a set of points (currently only 4 is supported. no other
+ * number for @p count will work). That is empty and ready to be modified
+ * with evas_map calls.
+ * 
+ * @param count number of points in the map. *
+ * @return a newly allocated map or NULL on errors.
  *
  * @see evas_map_free()
  * @see evas_map_dup()
@@ -196,7 +280,7 @@ evas_object_map_get(const Evas_Object *obj)
  * @see evas_object_map_set()
  */
 EAPI Evas_Map *
-evas_map_new(unsigned long count)
+evas_map_new(int count)
 {
    if (count != 4)
      {
@@ -208,10 +292,11 @@ evas_map_new(unsigned long count)
 
 /**
  * Copy a previously allocated map.
+ * 
+ * This makes a duplicate of the @p m object and returns it.
  *
- * @param m map to copy. Must not be @c NULL.
- *
- * @return newly allocated map with the same count and contents as @a m.
+ * @param m map to copy. Must not be NULL.
+ * @return newly allocated map with the same count and contents as @p m.
  */
 EAPI Evas_Map *
 evas_map_dup(const Evas_Map *m)
@@ -221,9 +306,12 @@ evas_map_dup(const Evas_Map *m)
 }
 
 /**
- * Destroys a previously allocated map.
+ * Free a previously allocated map.
  *
- * @param m map to destroy. Must not be @c NULL.
+ * This frees a givem map @p m and all memory associated with it. You must NOT
+ * free a map returned by evas_object_map_get() as this is internal.
+ * 
+ * @param m map to free.
  */
 EAPI void
 evas_map_free(Evas_Map *m)
@@ -234,18 +322,33 @@ evas_map_free(Evas_Map *m)
 
 /**
  * Change the map point's coordinate.
+ * 
+ * This sets the fixen point's coordinate in the map. Note that points
+ * describe the outline of a quadrangle and are ordered either clockwise
+ * or anit-clock-wise. It is suggested to keep your quadrangles concave and
+ * non-complex, though these polygon modes may work, they may not render
+ * a desired set of output. The quadrangle will use points 0 and 1 , 1 and 2,
+ * 2 and 3, and 3 and 0 to describe the edges of the quandrangle.
+ * 
+ * The X and Y and Z coordinates are in canvas units. Z is optional and may
+ * or may not be honored in drawing. Z is a hint and does not affect the
+ * X and Y rendered coordinates. It may be used for calculating fills with
+ * perspective correct rendering.
+ * 
+ * Remember all coordinates are canvas global ones like with move and reize
+ * in evas.
  *
  * @param m map to change point. Must not be @c NULL.
  * @param idx index of point to change. Must be smaller than map size.
- * @param x TODO
- * @param y TODO
- * @param z TODO
+ * @param x Point X Coordinate
+ * @param y Point Y Coordinate
+ * @param z Point Z Coordinate hint (pre-perspective transform)
  *
  * @see evas_map_util_rotate()
  * @see evas_map_util_zoom()
  */
 EAPI void
-evas_map_point_coord_set(Evas_Map *m, unsigned long idx, Evas_Coord x, Evas_Coord y, Evas_Coord z)
+evas_map_point_coord_set(Evas_Map *m, int idx, Evas_Coord x, Evas_Coord y, Evas_Coord z)
 {
    Evas_Map_Point *p;
    if (!m) return;
@@ -258,20 +361,20 @@ evas_map_point_coord_set(Evas_Map *m, unsigned long idx, Evas_Coord x, Evas_Coor
 
 /**
  * Get the map point's coordinate.
+ * 
+ * This returns the coordinates of the given point in the map.
  *
- * @param m map to query point. Must not be @c NULL.
+ * @param m map to query point.
  * @param idx index of point to query. Must be smaller than map size.
- * @param x where to return TODO. If non @c NULL, it's guaranteed to
- *        be set (on error it's set to zero).
- * @param y where to return TODO. If non @c NULL, it's guaranteed to
- *        be set (on error it's set to zero).
- * @param z where to return TODO. If non @c NULL, it's guaranteed to
- *        be set (on error it's set to zero).
+ * @param x where to return the X coordinate.
+ * @param y where to return the Y coordinate.
+ * @param z where to return the Z coordinate.
  */
 EAPI void
-evas_map_point_coord_get(const Evas_Map *m, unsigned long idx, Evas_Coord *x, Evas_Coord *y, Evas_Coord *z)
+evas_map_point_coord_get(const Evas_Map *m, int idx, Evas_Coord *x, Evas_Coord *y, Evas_Coord *z)
 {
    const Evas_Map_Point *p;
+   
    if (!m) goto error;
    if (idx >= m->count) goto error;
    p = m->points + idx;
@@ -287,15 +390,24 @@ evas_map_point_coord_get(const Evas_Map *m, unsigned long idx, Evas_Coord *x, Ev
 }
 
 /**
- * Change the map point's TODO.
+ * Change the map point's U and V texture source point
  *
- * @param m map to change point. Must not be @c NULL.
+ * This sets the U and V coordinates for the point. This determines which
+ * coordinate in the source image is mapped to the given point, much like
+ * OpenGL and textures. Notes that these points do select the pixel, but
+ * are double floating point values to allow for accuracy and sub-pixel
+ * selection.
+ * 
+ * @param m map to change the point of.
  * @param idx index of point to change. Must be smaller than map size.
- * @param u TODO
- * @param v TODO
+ * @param u the X coordinate within the image/texture source
+ * @param v the Y coordinate within the image/texture source
+ * 
+ * @see evas_map_point_coord_set()
+ * @see evas_object_map_set()
  */
 EAPI void
-evas_map_point_image_uv_set(Evas_Map *m, unsigned long idx, double u, double v)
+evas_map_point_image_uv_set(Evas_Map *m, int idx, double u, double v)
 {
    Evas_Map_Point *p;
    if (!m) return;
@@ -306,17 +418,17 @@ evas_map_point_image_uv_set(Evas_Map *m, unsigned long idx, double u, double v)
 }
 
 /**
- * Get the map point's TODO.
+ * Get the map point's U and V texture source points
  *
- * @param m map to query point. Must not be @c NULL.
+ * This returns the texture points set by evas_map_point_image_uv_set().
+ * 
+ * @param m map to query point.
  * @param idx index of point to query. Must be smaller than map size.
- * @param u where to return TODO. If non @c NULL, it's guaranteed to
- *        be set (on error it's set to zero).
- * @param v where to return TODO. If non @c NULL, it's guaranteed to
- *        be set (on error it's set to zero).
+ * @param u where to write the X coordinate within the image/texture source
+ * @param v where to write the Y coordinate within the image/texture source
  */
 EAPI void
-evas_map_point_image_uv_get(const Evas_Map *m, unsigned long idx, double *u, double *v)
+evas_map_point_image_uv_get(const Evas_Map *m, int idx, double *u, double *v)
 {
    const Evas_Map_Point *p;
    if (!m) goto error;
@@ -331,16 +443,26 @@ evas_map_point_image_uv_get(const Evas_Map *m, unsigned long idx, double *u, dou
    if (v) *v = 0.0;
 }
 
+/****************************************************************************/
+/* util functions for manipulating maps, so you don't need to know the math */
+/****************************************************************************/
+
 /**
- * Change the map to apply the given rotation to object.
+ * Change the map to apply the given rotation.
+ * 
+ * This rotates the indicated map's coordinates around the center coordinate
+ * given by @p cx and @p cy as the rotation center. The points will have their
+ * X and Y coordinates rotated clockwise by @p degrees degress (360.0 is a
+ * full rotation). Negative values for degrees will rotate counter-clockwise
+ * by that amount. All coordinates are canvas global coordinates.
  *
- * @param m map to change. Must not be @c NULL.
- * @param degrees amount of degrees from 0.0 to 360.0 to rotate the
- *        object. This is the canonical reference, counter-clockwise. TODO
- * @param cx rotation's center horizontal positon. TODO (offset from object center? left?)
- * @param cy rotation's center vertical positon. TODO (offset from object center? top?)
+ * @param m map to change.
+ * @param degrees amount of degrees from 0.0 to 360.0 to rotate.
+ * @param cx rotation's center horizontal positon.
+ * @param cy rotation's center vertical positon.
  *
  * @see evas_map_point_coord_set()
+ * @see evas_map_util_zoom()
  */
 EAPI void
 evas_map_util_rotate(Evas_Map *m, double degrees, Evas_Coord cx, Evas_Coord cy)
@@ -372,15 +494,22 @@ evas_map_util_rotate(Evas_Map *m, double degrees, Evas_Coord cx, Evas_Coord cy)
 }
 
 /**
- * Change the map to apply the given zooming to object.
+ * Change the map to apply the given zooming.
  *
- * @param m map to change. Must not be @c NULL.
+ * Like evas_map_util_rotate(), this zooms the points of the map from a center
+ * point. That center is defined by @p cx and @p cy. The @p zoomx and @p zoomy
+ * parameters specific how much to zoom in the X and Y direction respectively.
+ * A value of 1.0 means "don't zoom". 2.0 means "dobule the size". 0.5 is
+ * "half the size" etc. All coordinates are canvas global coordinates.
+ * 
+ * @param m map to change.
  * @param zoomx horizontal zoom to use.
  * @param zoomy vertical zoom to use.
- * @param cx zooming center horizontal positon. TODO (offset from object center? left?)
- * @param cy zooming center vertical positon. TODO (offset from object center? top?)
+ * @param cx zooming center horizontal positon.
+ * @param cy zooming center vertical positon.
  *
  * @see evas_map_point_coord_set()
+ * @see evas_map_util_rotate()
  */
 EAPI void
 evas_map_util_zoom(Evas_Map *m, double zoomx, double zoomy, Evas_Coord cx, Evas_Coord cy)
index b7be14e..2cbc606 100644 (file)
@@ -78,6 +78,7 @@ static const Evas_Object_Func object_func =
      NULL,
      NULL,
      NULL,
+     NULL,
      NULL
 };
 
index 3c02a95..a23dda9 100644 (file)
@@ -63,6 +63,7 @@ static const Evas_Object_Func object_func =
      NULL,
      NULL,
      NULL,
+     NULL,
      NULL
 };
 
index 1095521..3b6910e 100644 (file)
@@ -63,6 +63,7 @@ static const Evas_Object_Func rg_object_func =
      NULL,
      NULL,
      NULL,
+     NULL,
      NULL
 };
 
index 6cdf5e1..0e49ca1 100644 (file)
@@ -87,6 +87,7 @@ static int evas_object_image_was_opaque(Evas_Object *obj);
 static int evas_object_image_is_inside(Evas_Object *obj, Evas_Coord x, Evas_Coord y);
 static int evas_object_image_has_opaque_rect(Evas_Object *obj);
 static int evas_object_image_get_opaque_rect(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h);
+static int evas_object_image_can_map(Evas_Object *obj);
 
 static void *evas_object_image_data_convert_internal(Evas_Object_Image *o, void *data, Evas_Colorspace to_cspace);
 static void evas_object_image_filled_resize_listener(void *data, Evas *e, Evas_Object *obj, void *einfo);
@@ -113,7 +114,8 @@ static const Evas_Object_Func object_func =
      NULL,
      NULL,
      evas_object_image_has_opaque_rect,
-     evas_object_image_get_opaque_rect
+     evas_object_image_get_opaque_rect,
+     evas_object_image_can_map
 };
 
 /**
@@ -3004,6 +3006,12 @@ evas_object_image_get_opaque_rect(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y
    return 1;
 }
 
+static int
+evas_object_image_can_map(Evas_Object *obj)
+{
+   return 1;
+}
+
 static void *
 evas_object_image_data_convert_internal(Evas_Object_Image *o, void *data, Evas_Colorspace to_cspace)
 {
index 1f3cafc..1539c76 100644 (file)
@@ -65,6 +65,7 @@ static const Evas_Object_Func object_func =
      evas_object_line_coords_recalc,
      NULL,
      NULL,
+     NULL,
      NULL
 };
 
index a623529..c93383e 100644 (file)
@@ -383,6 +383,7 @@ evas_object_del(Evas_Object *obj)
    while (obj->clip.clipees) evas_object_clip_unset(obj->clip.clipees->data);
    if (obj->cur.clipper) evas_object_clip_unset(obj);
    if (obj->smart.smart) evas_object_smart_del(obj);
+   evas_object_map_set(obj, NULL);
    evas_object_event_callback_call(obj, EVAS_CALLBACK_FREE, NULL);
    evas_object_smart_cleanup(obj);
    obj->delete_me = 1;
index 44c053f..2b3109e 100644 (file)
@@ -62,6 +62,7 @@ static const Evas_Object_Func object_func =
      NULL,
      NULL,
      NULL,
+     NULL,
      NULL
 };
 
index 9d6b3ce..0b8f06f 100644 (file)
@@ -59,6 +59,7 @@ static const Evas_Object_Func object_func =
      NULL,
      NULL,
      NULL,
+     NULL,
      NULL
 };
 
index cb9b622..579d3c6 100644 (file)
@@ -59,6 +59,7 @@ static const Evas_Object_Func object_func =
      NULL,
      NULL,
      NULL,
+     NULL,
      NULL
 };
 
index 39fbf89..b45fb19 100644 (file)
@@ -185,6 +185,7 @@ static const Evas_Object_Func object_func =
      evas_object_textblock_coords_recalc,
      evas_object_textblock_scale_update,
      NULL,
+     NULL,
      NULL
 };
 
index 99e3277..24a4f40 100644 (file)
@@ -2,7 +2,7 @@
 #include "evas_private.h"
 
 static Eina_List *
-evas_render_updates_internal(Evas *e, unsigned char make_updates, unsigned char do_draw);
+evas_render_updates_internal(Evas *e, Evas_Object *smart, unsigned char make_updates, unsigned char do_draw);
 
 /**
  * Add a damage rectangle.
@@ -144,6 +144,39 @@ _evas_render_phase1_object_process(Evas *e, Evas_Object *obj, Eina_Array *active
        obj->changed = 1;
        clean_them = EINA_TRUE;
      }
+   
+   if (!((obj->func->can_map) && (obj->func->can_map(obj))) &&
+       ((obj->cur.map) && (obj->cur.map->count == 4) && (obj->cur.usemap)))
+     {
+        if (obj->changed)
+          {
+             if ((is_active) && (obj->restack) && (!obj->clip.clipees) &&
+                 ((evas_object_is_visible(obj) && (!obj->cur.have_clipees)) ||
+                  (evas_object_was_visible(obj) && (!obj->prev.have_clipees))))
+               eina_array_push(restack_objects, obj);
+             else if ((is_active) && (!obj->clip.clipees) &&
+                      ((evas_object_is_visible(obj) && (!obj->cur.have_clipees)) ||
+                       (evas_object_was_visible(obj) && (!obj->prev.have_clipees))))
+               {
+                  eina_array_push(render_objects, obj);
+                  obj->render_pre = 1;
+               }
+          }
+        /* for now all mapped objects are no logner opaque        
+        else
+          {
+             if (evas_object_is_opaque(obj) &&
+                 evas_object_is_visible(obj))
+               {
+                  eina_array_push(render_objects, obj);
+                  obj->rect_del = 1;
+               }
+          }
+         */
+     }
+   
+   /* handle normal rendering. this object knows how to handle maps */
+   
    if (obj->changed)
      {
        if (obj->smart.smart)
@@ -246,14 +279,14 @@ _evas_render_check_pending_objects(Eina_Array *pending_objects, Evas *e)
        Evas_Object *obj;
        int ok = 0;
        int is_active;
-
+        
        obj = eina_array_data_get(pending_objects, i);
-
+        
        if (!obj->layer) goto clean_stuff;
-
+        
        evas_object_clip_recalc(obj);
        is_active = evas_object_is_active(obj);
-
+        
        if (!is_active &&
            !obj->is_active &&
            !obj->render_pre &&
@@ -262,7 +295,7 @@ _evas_render_check_pending_objects(Eina_Array *pending_objects, Evas *e)
             ok = 1;
             goto clean_stuff;
          }
-
+        
        if (obj->is_active == is_active)
          {
             if (obj->changed)
@@ -279,18 +312,18 @@ _evas_render_check_pending_objects(Eina_Array *pending_objects, Evas *e)
                         (evas_object_was_visible(obj) && (!obj->prev.have_clipees))))
                      {
                         if (!(obj->render_pre
-                              || obj->rect_del))
+                               || obj->rect_del))
                           ok = 1;
                      }
-                   else
-                     if (is_active && (!obj->clip.clipees) &&
-                         ((evas_object_is_visible(obj) && (!obj->cur.have_clipees)) ||
-                          (evas_object_was_visible(obj) && (!obj->prev.have_clipees))))
-                       {
-                          if (obj->render_pre
-                              || obj->rect_del)
-                            ok = 1;
-                       }
+                  else
+                    if (is_active && (!obj->clip.clipees) &&
+                        ((evas_object_is_visible(obj) && (!obj->cur.have_clipees)) ||
+                         (evas_object_was_visible(obj) && (!obj->prev.have_clipees))))
+                      {
+                         if (obj->render_pre
+                             || obj->rect_del)
+                           ok = 1;
+                      }
               }
             else
               {
@@ -303,18 +336,18 @@ _evas_render_check_pending_objects(Eina_Array *pending_objects, Evas *e)
                      }
               }
          }
-
-     clean_stuff:
+        
+        clean_stuff:
        if (!ok)
          {
             eina_array_clean(&e->active_objects);
             eina_array_clean(&e->render_objects);
-
+             
             eina_array_clean(&e->restack_objects);
             eina_array_clean(&e->delete_objects);
-
+             
             e->invalidate = 1;
-
+             
             return ;
          }
      }
@@ -332,7 +365,10 @@ pending_change(void *data, void *gdata __UNUSED__)
 }
 
 static Eina_List *
-evas_render_updates_internal(Evas *e, unsigned char make_updates, unsigned char do_draw)
+evas_render_updates_internal(Evas *e,
+                             Evas_Object *smart,
+                             unsigned char make_updates,
+                             unsigned char do_draw)
 {
    Eina_List *updates = NULL;
    Eina_List *ll;
@@ -349,6 +385,11 @@ evas_render_updates_internal(Evas *e, unsigned char make_updates, unsigned char
    MAGIC_CHECK_END();
    if (!e->changed) return NULL;
 
+   if (smart)
+     {
+        // FIXME: if smart, only consider child objects
+     }
+
    evas_call_smarts_calculate(e);
 
    /* Check if the modified object mean recalculating every thing */
@@ -588,11 +629,79 @@ evas_render_updates_internal(Evas *e, unsigned char make_updates, unsigned char
                                    }
                              }
 #endif
-                           obj->func->render(obj,
-                                             e->engine.data.output,
-                                             e->engine.data.context,
-                                             surface,
-                                             off_x, off_y);
+                            if (!((obj->func->can_map) && (obj->func->can_map(obj))) &&
+                                ((obj->cur.map) && (obj->cur.map->count == 4) && (obj->cur.usemap)))
+                              {
+                                 const Evas_Map_Point *p, *p_end;
+                                 RGBA_Map_Point pts[4], *pt;
+                                 void *ctx;
+                                 
+                                 ctx = e->engine.func->context_new(e->engine.data.output);
+                                 if (!obj->cur.map->surface)
+                                   {
+                                      obj->cur.map->surface =
+                                        obj->layer->evas->engine.func->image_map_surface_new
+                                        (e->engine.data.output,
+                                         obj->cur.map->normal_geometry.w,
+                                         obj->cur.map->normal_geometry.h,
+                                         1);
+                                   }
+                                 
+                                 if (obj->smart.smart)
+                                   {
+                                      // FIXME: doesnt work yet
+                                      // smart object. draw all children to
+                                      // surface (and if they are mapped...
+                                      // recurse)
+                                      evas_render_updates_internal(e, obj, 0, 1);
+                                   }
+                                 else
+                                   {
+                                      obj->func->render(obj,
+                                                        e->engine.data.output,
+                                                        ctx,
+                                                        obj->cur.map->surface,
+                                                        -obj->cur.cache.clip.x,
+                                                        -obj->cur.cache.clip.y
+                                                        );
+                                   }
+                                 e->engine.func->context_free(e->engine.data.output, ctx);
+                                 
+                                 p = obj->cur.map->points;
+                                 p_end = p + 4;
+                                 pt = pts;
+                                 
+                                 for (; p < p_end; p++, pt++)
+                                   {
+                                      pt->x = (p->x + off_x) << FP;
+                                      pt->y = (p->y + off_y) << FP;
+                                      pt->z = (p->z)         << FP;
+                                      pt->u = p->u * FP1;
+                                      pt->v = p->v * FP1;
+                                   }
+                                 obj->layer->evas->engine.func->image_map4_draw
+                                   (e->engine.data.output,
+                                    e->engine.data.context,
+                                    surface,
+                                    obj->cur.map->surface,
+                                    pts,
+                                    1, // smooth? (on for now)
+                                    0);
+                                 // FIXME: needs to cache these maps and
+                                 // keep them only rendering updates
+                                 obj->layer->evas->engine.func->image_map_surface_free
+                                   (e->engine.data.output,
+                                    obj->cur.map->surface);
+                                 obj->cur.map->surface = NULL;
+                              }
+                            else
+                              {
+                                 obj->func->render(obj,
+                                                   e->engine.data.output,
+                                                   e->engine.data.context,
+                                                   surface,
+                                                   off_x, off_y);
+                              }
                            e->engine.func->context_cutout_clear(e->engine.data.output,
                                                                 e->engine.data.context);
                         }
@@ -703,7 +812,7 @@ evas_render_updates(Evas *e)
    MAGIC_CHECK_END();
 
    if (!e->changed) return NULL;
-   return evas_render_updates_internal(e, 1, 1);
+   return evas_render_updates_internal(e, NULL, 1, 1);
 }
 
 /**
@@ -722,7 +831,7 @@ evas_render(Evas *e)
    MAGIC_CHECK_END();
 
    if (!e->changed) return;
-   evas_render_updates_internal(e, 0, 1);
+   evas_render_updates_internal(e, NULL, 0, 1);
 }
 
 /**
@@ -746,7 +855,7 @@ evas_norender(Evas *e)
    MAGIC_CHECK_END();
 
 //   if (!e->changed) return;
-   evas_render_updates_internal(e, 0, 0);
+   evas_render_updates_internal(e, NULL, 0, 0);
 }
 
 /**
index 9892083..3b19aab 100644 (file)
@@ -366,7 +366,9 @@ struct _Evas_Map_Point
 
 struct _Evas_Map
 {
-   unsigned long count;
+   int count;
+   Evas_Coord_Rectangle normal_geometry;
+   void *surface;
    Evas_Map_Point points[];
 };
 
@@ -537,6 +539,8 @@ struct _Evas_Object_Func
 
    int (*has_opaque_rect) (Evas_Object *obj);
    int (*get_opaque_rect) (Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Evas_Coord *w, Evas_Coord *h);
+
+   int (*can_map) (Evas_Object *obj);
 };
 
 struct _Evas_Func
@@ -689,6 +693,8 @@ struct _Evas_Func
    int  (*font_last_up_to_pos)             (void *data, void *font, const char *text, int x, int y);
 
    void (*image_map4_draw)                 (void *data, void *context, void *surface, void *image, RGBA_Map_Point *p, int smooth, int level);
+   void *(*image_map_surface_new)          (void *data, int w, int h, int alpha);
+   void *(*image_map_surface_free)         (void *data, void *surface);
 };
 
 struct _Evas_Image_Load_Func
index a6a9923..90a4f1a 100644 (file)
@@ -253,7 +253,10 @@ static Evas_Func eng_func =
      eng_image_scale_hint_set,
      eng_image_scale_hint_get,
      /* more font draw functions */
-     eng_font_last_up_to_pos
+     eng_font_last_up_to_pos,
+     NULL, // image_map4_draw
+     NULL, // image_map_surface_new
+     NULL // image_map_surface_free
 };
 
 static void *
index 35d0683..8514f75 100644 (file)
@@ -580,6 +580,10 @@ module_open(Evas_Module *em)
    ORD(image_scale_hint_set);
    ORD(image_scale_hint_get);
 
+//   ORD(image_map4_draw);
+//   ORD(image_map_surface_new);
+//   ORD(image_map_surface_free);
+
 /*
    ORD(gradient2_color_np_stop_insert);
    ORD(gradient2_clear);
index bee8460..91a751e 100644 (file)
@@ -1679,6 +1679,11 @@ module_open(Evas_Module *em)
    ORD(gradient_draw);
    ORD(image_scale_hint_set);
    ORD(image_scale_hint_get);
+
+//   ORD(image_map4_draw);
+//   ORD(image_map_surface_new);
+//   ORD(image_map_surface_free);
+
    /* now advertise out own api */
    em->functions = (void *)(&func);
    return 1;
index f508f06..eb1f436 100644 (file)
@@ -1175,6 +1175,10 @@ module_open(Evas_Module *em)
    ORD(image_scale_hint_set);
    ORD(image_scale_hint_get);
    
+   //ODR(image_map4_draw);
+   //ODR(image_map_surface_new);
+   //ODR(image_map_surface_free);
+   
    /* now advertise out own api */
    em->functions = (void *)(&func);
    return 1;
index 5f522ac..22f0e69 100644 (file)
@@ -1512,7 +1512,10 @@ module_open(Evas_Module *em)
 
    ORD(image_scale_hint_set);
    ORD(image_scale_hint_get);
-   
+
+//   ORD(image_map4_draw);
+//   ORD(image_map_surface_new);
+//   ORD(image_map_surface_free);
    /* now advertise out our api */
    em->functions = (void *)(&func);
    return 1;
index e366359..3fa448d 100644 (file)
@@ -1012,6 +1012,10 @@ static Evas_Func func =
      /* more font draw functions */
      eng_font_last_up_to_pos
      /* FUTURE software generic calls go here */
+//   ORD(image_map4_draw);
+//   ORD(image_map_surface_new);
+//   ORD(image_map_surface_free);
+     /* FUTURE software generic calls go here */
 };
 
 /*
index eded318..e4af6fa 100644 (file)
@@ -787,6 +787,26 @@ eng_image_map4_draw(void *data __UNUSED__, void *context, void *surface, void *i
    evas_common_cpu_end_opt();
 }
 
+static void *
+eng_image_map_surface_new(void *data __UNUSED__, int w, int h, int alpha)
+{
+   void *surface;
+   DATA32 *pixels;
+   surface = evas_cache_image_copied_data(evas_common_image_cache_get(), 
+                                          w, h, NULL, alpha, 
+                                          EVAS_COLORSPACE_ARGB8888);
+   pixels = evas_cache_image_pixels(surface);
+   // FIXME: need a clear call
+   memset(pixels, 0, (w *h * sizeof(DATA32)));
+   return surface;
+}
+
+static void
+eng_image_map_surface_free(void *data __UNUSED__, void *surface)
+{
+   evas_cache_image_drop(surface);
+}
+
 static void
 eng_image_scale_hint_set(void *data __UNUSED__, void *image, int hint)
 {
@@ -1135,7 +1155,9 @@ static Evas_Func func =
      /* more font draw functions */
      eng_font_last_up_to_pos,
      /* FUTURE software generic calls go here (done) */
-     eng_image_map4_draw
+     eng_image_map4_draw,
+     eng_image_map_surface_new,
+     eng_image_map_surface_free
      /* FUTURE software generic calls go here */
 };
 
index 3fd4b07..32d9300 100644 (file)
@@ -1500,6 +1500,10 @@ module_open(Evas_Module *em)
    
    ORD(image_scale_hint_set);
    ORD(image_scale_hint_get);
+
+//   ORD(image_map4_draw);
+//   ORD(image_map_surface_new);
+//   ORD(image_map_surface_free);
    
    /* now advertise out own api */
    em->functions = (void *)(&func);