the start of other objects being able to map! text objects work.. tested.

SVN revision: 43323
This commit is contained in:
Carsten Haitzler 2009-10-28 08:59:01 +00:00
parent 2b81de7c58
commit 5cc7803ef9
22 changed files with 455 additions and 145 deletions

View 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;

View 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.
* Create 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.
*
* @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)

View File

@ -78,6 +78,7 @@ static const Evas_Object_Func object_func =
NULL,
NULL,
NULL,
NULL,
NULL
};

View File

@ -63,6 +63,7 @@ static const Evas_Object_Func object_func =
NULL,
NULL,
NULL,
NULL,
NULL
};

View File

@ -63,6 +63,7 @@ static const Evas_Object_Func rg_object_func =
NULL,
NULL,
NULL,
NULL,
NULL
};

View 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)
{

View File

@ -65,6 +65,7 @@ static const Evas_Object_Func object_func =
evas_object_line_coords_recalc,
NULL,
NULL,
NULL,
NULL
};

View 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;

View File

@ -62,6 +62,7 @@ static const Evas_Object_Func object_func =
NULL,
NULL,
NULL,
NULL,
NULL
};

View File

@ -59,6 +59,7 @@ static const Evas_Object_Func object_func =
NULL,
NULL,
NULL,
NULL,
NULL
};

View File

@ -59,6 +59,7 @@ static const Evas_Object_Func object_func =
NULL,
NULL,
NULL,
NULL,
NULL
};

View 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
};

View 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);
}
/**

View 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

View 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 *

View 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);

View 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;

View 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;

View 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;

View 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 */
};
/*

View 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 */
};

View 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);