forked from enlightenment/efl
add EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN for accessibility
:) SVN revision: 67264
This commit is contained in:
parent
58c865325d
commit
4ae6816486
|
@ -638,3 +638,9 @@
|
||||||
* Add evas_object_smart_callback_del_full() to allow users to
|
* Add evas_object_smart_callback_del_full() to allow users to
|
||||||
unregister a specific smart event callback instead of all
|
unregister a specific smart event callback instead of all
|
||||||
callbacks matching a given type and function pointer.
|
callbacks matching a given type and function pointer.
|
||||||
|
|
||||||
|
2012-01-17 Carsten Haitzler (The Rasterman)
|
||||||
|
|
||||||
|
* Add EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN pointer mode
|
||||||
|
for some very specific behavior needed for accessibility.
|
||||||
|
|
||||||
|
|
|
@ -1065,7 +1065,8 @@ struct _Evas_Event_Hold /** Hold change event */
|
||||||
typedef enum _Evas_Object_Pointer_Mode
|
typedef enum _Evas_Object_Pointer_Mode
|
||||||
{
|
{
|
||||||
EVAS_OBJECT_POINTER_MODE_AUTOGRAB, /**< default, X11-like */
|
EVAS_OBJECT_POINTER_MODE_AUTOGRAB, /**< default, X11-like */
|
||||||
EVAS_OBJECT_POINTER_MODE_NOGRAB /**< pointer always bound to the object right below it */
|
EVAS_OBJECT_POINTER_MODE_NOGRAB, /**< pointer always bound to the object right below it */
|
||||||
|
EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN /**< useful on object with "repeat events" enabled, where mouse/touch up and down events WONT be repeated to objects and these objects wont be auto-grabbed. @since 1.2 */
|
||||||
} Evas_Object_Pointer_Mode; /**< How the mouse pointer should be handled by Evas. */
|
} Evas_Object_Pointer_Mode; /**< How the mouse pointer should be handled by Evas. */
|
||||||
|
|
||||||
typedef void (*Evas_Smart_Cb) (void *data, Evas_Object *obj, void *event_info); /**< Evas smart objects' "smart callback" function signature */
|
typedef void (*Evas_Smart_Cb) (void *data, Evas_Object *obj, void *event_info); /**< Evas smart objects' "smart callback" function signature */
|
||||||
|
|
|
@ -1,6 +1,11 @@
|
||||||
#include "evas_common.h"
|
#include "evas_common.h"
|
||||||
#include "evas_private.h"
|
#include "evas_private.h"
|
||||||
|
|
||||||
|
static Eina_List *
|
||||||
|
_evas_event_object_list_in_get(Evas *e, Eina_List *in,
|
||||||
|
const Eina_Inlist *list, Evas_Object *stop,
|
||||||
|
int x, int y, int *no_rep);
|
||||||
|
|
||||||
static void
|
static void
|
||||||
_evas_event_havemap_adjust(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Eina_Bool mouse_grabbed)
|
_evas_event_havemap_adjust(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Eina_Bool mouse_grabbed)
|
||||||
{
|
{
|
||||||
|
@ -16,15 +21,17 @@ _evas_event_havemap_adjust(Evas_Object *obj, Evas_Coord *x, Evas_Coord *y, Eina_
|
||||||
}
|
}
|
||||||
|
|
||||||
static Eina_List *
|
static Eina_List *
|
||||||
_evas_event_object_list_in_get(Evas *e, Eina_List *in,
|
_evas_event_object_list_raw_in_get(Evas *e, Eina_List *in,
|
||||||
const Eina_Inlist *list, Evas_Object *stop,
|
const Eina_Inlist *list, Evas_Object *stop,
|
||||||
int x, int y, int *no_rep)
|
int x, int y, int *no_rep)
|
||||||
{
|
{
|
||||||
Evas_Object *obj;
|
Evas_Object *obj;
|
||||||
int inside;
|
int inside;
|
||||||
|
|
||||||
if (!list) return in;
|
if (!list) return in;
|
||||||
EINA_INLIST_REVERSE_FOREACH(list, obj)
|
for (obj = _EINA_INLIST_CONTAINER(obj, list);
|
||||||
|
obj;
|
||||||
|
obj = _EINA_INLIST_CONTAINER(obj, EINA_INLIST_GET(obj)->prev))
|
||||||
{
|
{
|
||||||
if (obj == stop)
|
if (obj == stop)
|
||||||
{
|
{
|
||||||
|
@ -113,6 +120,16 @@ _evas_event_object_list_in_get(Evas *e, Eina_List *in,
|
||||||
return in;
|
return in;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static Eina_List *
|
||||||
|
_evas_event_object_list_in_get(Evas *e, Eina_List *in,
|
||||||
|
const Eina_Inlist *list, Evas_Object *stop,
|
||||||
|
int x, int y, int *no_rep)
|
||||||
|
{
|
||||||
|
if (!list) return NULL;
|
||||||
|
return _evas_event_object_list_raw_in_get(e, in, list->last, stop,
|
||||||
|
x, y, no_rep);
|
||||||
|
}
|
||||||
|
|
||||||
Eina_List *
|
Eina_List *
|
||||||
evas_event_objects_event_list(Evas *e, Evas_Object *stop, int x, int y)
|
evas_event_objects_event_list(Evas *e, Evas_Object *stop, int x, int y)
|
||||||
{
|
{
|
||||||
|
@ -275,10 +292,16 @@ evas_event_feed_mouse_down(Evas *e, int b, Evas_Button_Flags flags, unsigned int
|
||||||
copy = evas_event_list_copy(e->pointer.object.in);
|
copy = evas_event_list_copy(e->pointer.object.in);
|
||||||
EINA_LIST_FOREACH(copy, l, obj)
|
EINA_LIST_FOREACH(copy, l, obj)
|
||||||
{
|
{
|
||||||
if (obj->pointer_mode != EVAS_OBJECT_POINTER_MODE_NOGRAB)
|
if ((obj->pointer_mode == EVAS_OBJECT_POINTER_MODE_AUTOGRAB) ||
|
||||||
|
(obj->pointer_mode == EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN))
|
||||||
{
|
{
|
||||||
obj->mouse_grabbed += addgrab + 1;
|
obj->mouse_grabbed += addgrab + 1;
|
||||||
e->pointer.mouse_grabbed += addgrab + 1;
|
e->pointer.mouse_grabbed += addgrab + 1;
|
||||||
|
if (obj->pointer_mode == EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN)
|
||||||
|
{
|
||||||
|
e->pointer.nogrep++;
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
EINA_LIST_FOREACH(copy, l, obj)
|
EINA_LIST_FOREACH(copy, l, obj)
|
||||||
|
@ -291,6 +314,8 @@ evas_event_feed_mouse_down(Evas *e, int b, Evas_Button_Flags flags, unsigned int
|
||||||
if (e->events_frozen <= 0)
|
if (e->events_frozen <= 0)
|
||||||
evas_object_event_callback_call(obj, EVAS_CALLBACK_MOUSE_DOWN, &ev, event_id);
|
evas_object_event_callback_call(obj, EVAS_CALLBACK_MOUSE_DOWN, &ev, event_id);
|
||||||
if (e->delete_me) break;
|
if (e->delete_me) break;
|
||||||
|
if (obj->pointer_mode == EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN)
|
||||||
|
break;
|
||||||
}
|
}
|
||||||
if (copy) eina_list_free(copy);
|
if (copy) eina_list_free(copy);
|
||||||
e->last_mouse_down_counter++;
|
e->last_mouse_down_counter++;
|
||||||
|
@ -454,7 +479,7 @@ evas_event_feed_mouse_up(Evas *e, int b, Evas_Button_Flags flags, unsigned int t
|
||||||
ev.canvas.x = e->pointer.x;
|
ev.canvas.x = e->pointer.x;
|
||||||
ev.canvas.y = e->pointer.y;
|
ev.canvas.y = e->pointer.y;
|
||||||
_evas_event_havemap_adjust(obj, &ev.canvas.x, &ev.canvas.y, obj->mouse_grabbed);
|
_evas_event_havemap_adjust(obj, &ev.canvas.x, &ev.canvas.y, obj->mouse_grabbed);
|
||||||
if ((obj->pointer_mode != EVAS_OBJECT_POINTER_MODE_NOGRAB) &&
|
if ((obj->pointer_mode == EVAS_OBJECT_POINTER_MODE_AUTOGRAB) &&
|
||||||
(obj->mouse_grabbed > 0))
|
(obj->mouse_grabbed > 0))
|
||||||
{
|
{
|
||||||
obj->mouse_grabbed--;
|
obj->mouse_grabbed--;
|
||||||
|
@ -466,6 +491,11 @@ evas_event_feed_mouse_up(Evas *e, int b, Evas_Button_Flags flags, unsigned int t
|
||||||
evas_object_event_callback_call(obj, EVAS_CALLBACK_MOUSE_UP, &ev, event_id);
|
evas_object_event_callback_call(obj, EVAS_CALLBACK_MOUSE_UP, &ev, event_id);
|
||||||
}
|
}
|
||||||
if (e->delete_me) break;
|
if (e->delete_me) break;
|
||||||
|
if (obj->pointer_mode == EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN)
|
||||||
|
{
|
||||||
|
if (e->pointer.nogrep > 0) e->pointer.nogrep--;
|
||||||
|
break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (copy) copy = eina_list_free(copy);
|
if (copy) copy = eina_list_free(copy);
|
||||||
e->last_mouse_up_counter++;
|
e->last_mouse_up_counter++;
|
||||||
|
@ -560,6 +590,7 @@ evas_event_feed_mouse_wheel(Evas *e, int direction, int z, unsigned int timestam
|
||||||
EAPI void
|
EAPI void
|
||||||
evas_event_feed_mouse_move(Evas *e, int x, int y, unsigned int timestamp, const void *data)
|
evas_event_feed_mouse_move(Evas *e, int x, int y, unsigned int timestamp, const void *data)
|
||||||
{
|
{
|
||||||
|
Evas_Object *nogrep_obj = NULL;
|
||||||
int px, py;
|
int px, py;
|
||||||
//// Evas_Coord pcx, pcy;
|
//// Evas_Coord pcx, pcy;
|
||||||
|
|
||||||
|
@ -635,6 +666,13 @@ evas_event_feed_mouse_move(Evas *e, int x, int y, unsigned int timestamp, const
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
outs = eina_list_append(outs, obj);
|
outs = eina_list_append(outs, obj);
|
||||||
|
if ((obj->pointer_mode == EVAS_OBJECT_POINTER_MODE_NOGRAB_NO_REPEAT_UPDOWN) &&
|
||||||
|
(e->pointer.nogrep > 0))
|
||||||
|
{
|
||||||
|
eina_list_free(copy);
|
||||||
|
nogrep_obj = obj;
|
||||||
|
goto nogrep;
|
||||||
|
}
|
||||||
if (e->delete_me) break;
|
if (e->delete_me) break;
|
||||||
}
|
}
|
||||||
_evas_post_event_callback_call(e);
|
_evas_post_event_callback_call(e);
|
||||||
|
@ -817,6 +855,160 @@ evas_event_feed_mouse_move(Evas *e, int x, int y, unsigned int timestamp, const
|
||||||
_evas_post_event_callback_call(e);
|
_evas_post_event_callback_call(e);
|
||||||
}
|
}
|
||||||
_evas_unwalk(e);
|
_evas_unwalk(e);
|
||||||
|
return;
|
||||||
|
nogrep:
|
||||||
|
{
|
||||||
|
Eina_List *ins = NULL;
|
||||||
|
Eina_List *newin = NULL;
|
||||||
|
Eina_List *l, *copy, *lst = NULL;
|
||||||
|
Evas_Event_Mouse_Move ev;
|
||||||
|
Evas_Event_Mouse_Out ev2;
|
||||||
|
Evas_Event_Mouse_In ev3;
|
||||||
|
Evas_Object *obj, *below_obj;
|
||||||
|
int event_id = 0, event_id2 = 0;
|
||||||
|
int norep = 0, breaknext = 0;
|
||||||
|
|
||||||
|
_evas_object_event_new();
|
||||||
|
|
||||||
|
event_id = _evas_event_counter;
|
||||||
|
ev.buttons = e->pointer.button;
|
||||||
|
ev.cur.output.x = e->pointer.x;
|
||||||
|
ev.cur.output.y = e->pointer.y;
|
||||||
|
ev.cur.canvas.x = e->pointer.x;
|
||||||
|
ev.cur.canvas.y = e->pointer.y;
|
||||||
|
ev.prev.output.x = px;
|
||||||
|
ev.prev.output.y = py;
|
||||||
|
ev.prev.canvas.x = px;
|
||||||
|
ev.prev.canvas.y = py;
|
||||||
|
ev.data = (void *)data;
|
||||||
|
ev.modifiers = &(e->modifiers);
|
||||||
|
ev.locks = &(e->locks);
|
||||||
|
ev.timestamp = timestamp;
|
||||||
|
ev.event_flags = e->default_event_flags;
|
||||||
|
|
||||||
|
ev2.buttons = e->pointer.button;
|
||||||
|
ev2.output.x = e->pointer.x;
|
||||||
|
ev2.output.y = e->pointer.y;
|
||||||
|
ev2.canvas.x = e->pointer.x;
|
||||||
|
ev2.canvas.y = e->pointer.y;
|
||||||
|
ev2.data = (void *)data;
|
||||||
|
ev2.modifiers = &(e->modifiers);
|
||||||
|
ev2.locks = &(e->locks);
|
||||||
|
ev2.timestamp = timestamp;
|
||||||
|
ev2.event_flags = e->default_event_flags;
|
||||||
|
|
||||||
|
ev3.buttons = e->pointer.button;
|
||||||
|
ev3.output.x = e->pointer.x;
|
||||||
|
ev3.output.y = e->pointer.y;
|
||||||
|
ev3.canvas.x = e->pointer.x;
|
||||||
|
ev3.canvas.y = e->pointer.y;
|
||||||
|
ev3.data = (void *)data;
|
||||||
|
ev3.modifiers = &(e->modifiers);
|
||||||
|
ev3.locks = &(e->locks);
|
||||||
|
ev3.timestamp = timestamp;
|
||||||
|
ev3.event_flags = e->default_event_flags;
|
||||||
|
|
||||||
|
/* go thru old list of in objects */
|
||||||
|
copy = evas_event_list_copy(e->pointer.object.in);
|
||||||
|
EINA_LIST_FOREACH(copy, l, obj)
|
||||||
|
{
|
||||||
|
if (breaknext)
|
||||||
|
{
|
||||||
|
lst = l;
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
if (obj == nogrep_obj) breaknext = 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* get all new in objects */
|
||||||
|
below_obj = evas_object_below_get(nogrep_obj);
|
||||||
|
if (below_obj)
|
||||||
|
ins = _evas_event_object_list_raw_in_get(e, NULL,
|
||||||
|
EINA_INLIST_GET(below_obj), NULL,
|
||||||
|
e->pointer.x, e->pointer.y,
|
||||||
|
&norep);
|
||||||
|
EINA_LIST_FOREACH(copy, l, obj)
|
||||||
|
{
|
||||||
|
newin = eina_list_append(newin, obj);
|
||||||
|
if (obj == nogrep_obj) break;
|
||||||
|
}
|
||||||
|
EINA_LIST_FOREACH(ins, l, obj)
|
||||||
|
{
|
||||||
|
newin = eina_list_append(newin, obj);
|
||||||
|
}
|
||||||
|
|
||||||
|
EINA_LIST_FOREACH(lst, l, obj)
|
||||||
|
{
|
||||||
|
/* if its under the pointer and its visible and its in the new */
|
||||||
|
/* in list */
|
||||||
|
// FIXME: i don't think we need this
|
||||||
|
// evas_object_clip_recalc(obj);
|
||||||
|
if ((e->events_frozen <= 0) &&
|
||||||
|
evas_object_is_in_output_rect(obj, x, y, 1, 1) &&
|
||||||
|
(evas_object_clippers_is_visible(obj) ||
|
||||||
|
obj->mouse_grabbed) &&
|
||||||
|
eina_list_data_find(newin, obj) &&
|
||||||
|
(!evas_event_passes_through(obj)) &&
|
||||||
|
(!evas_event_freezes_through(obj)) &&
|
||||||
|
(!obj->clip.clipees) &&
|
||||||
|
((!obj->precise_is_inside) || evas_object_is_inside(obj, x, y))
|
||||||
|
)
|
||||||
|
{
|
||||||
|
if ((px != x) || (py != y))
|
||||||
|
{
|
||||||
|
ev.cur.canvas.x = e->pointer.x;
|
||||||
|
ev.cur.canvas.y = e->pointer.y;
|
||||||
|
_evas_event_havemap_adjust(obj, &ev.cur.canvas.x, &ev.cur.canvas.y, obj->mouse_grabbed);
|
||||||
|
evas_object_event_callback_call(obj, EVAS_CALLBACK_MOUSE_MOVE, &ev, event_id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
/* otherwise it has left the object */
|
||||||
|
else
|
||||||
|
{
|
||||||
|
if (obj->mouse_in)
|
||||||
|
{
|
||||||
|
obj->mouse_in = 0;
|
||||||
|
ev2.canvas.x = e->pointer.x;
|
||||||
|
ev2.canvas.y = e->pointer.y;
|
||||||
|
_evas_event_havemap_adjust(obj, &ev2.canvas.x, &ev2.canvas.y, obj->mouse_grabbed);
|
||||||
|
if (e->events_frozen <= 0)
|
||||||
|
evas_object_event_callback_call(obj, EVAS_CALLBACK_MOUSE_OUT, &ev2, event_id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (e->delete_me) break;
|
||||||
|
}
|
||||||
|
_evas_post_event_callback_call(e);
|
||||||
|
|
||||||
|
_evas_object_event_new();
|
||||||
|
|
||||||
|
event_id2 = _evas_event_counter;
|
||||||
|
if (copy) copy = eina_list_free(copy);
|
||||||
|
/* go thru our current list of ins */
|
||||||
|
EINA_LIST_FOREACH(newin, l, obj)
|
||||||
|
{
|
||||||
|
ev3.canvas.x = e->pointer.x;
|
||||||
|
ev3.canvas.y = e->pointer.y;
|
||||||
|
_evas_event_havemap_adjust(obj, &ev3.canvas.x, &ev3.canvas.y, obj->mouse_grabbed);
|
||||||
|
/* if its not in the old list of ins send an enter event */
|
||||||
|
if (!eina_list_data_find(e->pointer.object.in, obj))
|
||||||
|
{
|
||||||
|
if (!obj->mouse_in)
|
||||||
|
{
|
||||||
|
obj->mouse_in = 1;
|
||||||
|
if (e->events_frozen <= 0)
|
||||||
|
evas_object_event_callback_call(obj, EVAS_CALLBACK_MOUSE_IN, &ev3, event_id2);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (e->delete_me) break;
|
||||||
|
}
|
||||||
|
/* free our old list of ins */
|
||||||
|
eina_list_free(e->pointer.object.in);
|
||||||
|
/* and set up the new one */
|
||||||
|
e->pointer.object.in = newin;
|
||||||
|
|
||||||
|
_evas_post_event_callback_call(e);
|
||||||
|
}
|
||||||
|
_evas_unwalk(e);
|
||||||
}
|
}
|
||||||
|
|
||||||
EAPI void
|
EAPI void
|
||||||
|
|
|
@ -304,6 +304,7 @@ struct _Evas
|
||||||
int downs;
|
int downs;
|
||||||
DATA32 button;
|
DATA32 button;
|
||||||
Evas_Coord x, y;
|
Evas_Coord x, y;
|
||||||
|
int nogrep;
|
||||||
struct {
|
struct {
|
||||||
Eina_List *in;
|
Eina_List *in;
|
||||||
} object;
|
} object;
|
||||||
|
@ -584,7 +585,7 @@ struct _Evas_Object
|
||||||
unsigned char recalculate_cycle;
|
unsigned char recalculate_cycle;
|
||||||
Eina_Clist calc_entry;
|
Eina_Clist calc_entry;
|
||||||
|
|
||||||
Evas_Object_Pointer_Mode pointer_mode : 1;
|
Evas_Object_Pointer_Mode pointer_mode : 2;
|
||||||
|
|
||||||
Eina_Bool store : 1;
|
Eina_Bool store : 1;
|
||||||
Eina_Bool pass_events : 1;
|
Eina_Bool pass_events : 1;
|
||||||
|
|
Loading…
Reference in New Issue