devilhorns pushed a commit to branch master.
commit a4d26ee3a83876cf2ee04cbff61ba40a525dcfbe
Author: Chris Michael <[email protected]>
Date: Wed Apr 10 15:24:25 2013 +0100
Add support for the e_surface smart object.
Add code to listen for the callbacks from e_surface and pass events
along to the wayland client.
Signed-off-by: Chris Michael <[email protected]>
---
src/modules/wl_desktop_shell/e_mod_main.c | 183 +++++++++++++++++++++++++++++-
1 file changed, 180 insertions(+), 3 deletions(-)
diff --git a/src/modules/wl_desktop_shell/e_mod_main.c
b/src/modules/wl_desktop_shell/e_mod_main.c
index 6be2d3b..cc3590b 100644
--- a/src/modules/wl_desktop_shell/e_mod_main.c
+++ b/src/modules/wl_desktop_shell/e_mod_main.c
@@ -30,6 +30,11 @@ static void
_e_wl_shell_shell_surface_type_reset(E_Wayland_Shell_Surface *ewss);
static void _e_wl_shell_shell_surface_cb_destroy(struct wl_listener *listener,
void *data EINA_UNUSED);
static int _e_wl_shell_shell_surface_cb_ping_timeout(void *data);
static void _e_wl_shell_shell_surface_cb_render_post(void *data, Evas *evas
EINA_UNUSED, void *event EINA_UNUSED);
+static void _e_wl_shell_shell_surface_cb_focus_in(void *data, Evas_Object *obj
EINA_UNUSED, void *event EINA_UNUSED);
+static void _e_wl_shell_shell_surface_cb_focus_out(void *data, Evas_Object
*obj EINA_UNUSED, void *event EINA_UNUSED);
+static void _e_wl_shell_shell_surface_cb_mouse_in(void *data, Evas_Object *obj
EINA_UNUSED, void *event EINA_UNUSED);
+static void _e_wl_shell_shell_surface_cb_mouse_out(void *data, Evas_Object
*obj EINA_UNUSED, void *event EINA_UNUSED);
+static void _e_wl_shell_shell_surface_cb_mouse_move(void *data, Evas_Object
*obj EINA_UNUSED, void *event);
/* shell surface interface prototypes */
static void _e_wl_shell_shell_surface_cb_pong(struct wl_client *client
EINA_UNUSED, struct wl_resource *resource, unsigned int serial);
@@ -382,7 +387,7 @@ _e_wl_shell_shell_surface_configure(E_Wayland_Surface *ews,
Evas_Coord x, Evas_C
else
return;
- printf("Configure Surface: %d %d %d %d\n", x, y, w, h);
+ /* printf("Configure Surface: %d %d %d %d\n", x, y, w, h); */
/* handle shell_surface type change */
if ((ewss->next_type != E_WAYLAND_SHELL_SURFACE_TYPE_NONE) &&
@@ -467,8 +472,21 @@ _e_wl_shell_shell_surface_map(E_Wayland_Surface *ews,
Evas_Coord x, Evas_Coord y
evas_object_resize(ews->obj, w, h);
evas_object_show(ews->obj);
+ /* hook smart object callbacks */
+ evas_object_smart_callback_add(ews->obj, "mouse_in",
+ _e_wl_shell_shell_surface_cb_mouse_in, ews);
+ evas_object_smart_callback_add(ews->obj, "mouse_out",
+ _e_wl_shell_shell_surface_cb_mouse_out, ews);
+ evas_object_smart_callback_add(ews->obj, "mouse_move",
+ _e_wl_shell_shell_surface_cb_mouse_move,
ews);
+ evas_object_smart_callback_add(ews->obj, "focus_in",
+ _e_wl_shell_shell_surface_cb_focus_in, ews);
+ evas_object_smart_callback_add(ews->obj, "focus_out",
+ _e_wl_shell_shell_surface_cb_focus_out, ews);
+
/* create the e border for this surface */
ews->bd = e_border_new(con, ecore_evas_window_get(ews->ee), 1, 1);
+ e_surface_border_input_set(ews->obj, ews->bd);
e_border_move_resize(ews->bd, x, y, w, h);
e_border_show(ews->bd);
@@ -493,7 +511,24 @@ _e_wl_shell_shell_surface_unmap(E_Wayland_Surface *ews)
wl_pointer_set_focus(input->wl.seat.pointer, NULL, 0, 0);
}
- if (ews->obj) evas_object_del(ews->obj);
+ if (ews->obj)
+ {
+ /* delete smart callbacks */
+ evas_object_smart_callback_del(ews->obj, "mouse_in",
+ _e_wl_shell_shell_surface_cb_mouse_in);
+ evas_object_smart_callback_del(ews->obj, "mouse_out",
+ _e_wl_shell_shell_surface_cb_mouse_out);
+ evas_object_smart_callback_del(ews->obj, "mouse_move",
+
_e_wl_shell_shell_surface_cb_mouse_move);
+ evas_object_smart_callback_del(ews->obj, "focus_in",
+ _e_wl_shell_shell_surface_cb_focus_in);
+ evas_object_smart_callback_del(ews->obj, "focus_out",
+ _e_wl_shell_shell_surface_cb_focus_out);
+
+ /* delete the object */
+ evas_object_del(ews->obj);
+ }
+
if (ews->ee) ecore_evas_free(ews->ee);
if (ews->bd) e_object_del(E_OBJECT(ews->bd));
@@ -608,6 +643,149 @@ _e_wl_shell_shell_surface_cb_render_post(void *data, Evas
*evas EINA_UNUSED, voi
}
}
+static void
+_e_wl_shell_shell_surface_cb_focus_in(void *data, Evas_Object *obj
EINA_UNUSED, void *event EINA_UNUSED)
+{
+ E_Wayland_Surface *ews = NULL;
+ E_Wayland_Input *input = NULL;
+ Eina_List *l = NULL;
+
+ /* try to cast data to our surface structure */
+ if (!(ews = data)) return;
+
+ /* if this surface is not visible, get out */
+ if (!ews->mapped) return;
+
+ /* loop the list of inputs */
+ EINA_LIST_FOREACH(_e_wl_comp->seats, l, input)
+ {
+ /* set keyboard focus */
+ wl_keyboard_set_focus(input->wl.seat.keyboard, &ews->wl.surface);
+
+ /* update the keyboard focus in the data device */
+ wl_data_device_set_keyboard_focus(&input->wl.seat);
+ }
+}
+
+static void
+_e_wl_shell_shell_surface_cb_focus_out(void *data, Evas_Object *obj
EINA_UNUSED, void *event EINA_UNUSED)
+{
+ E_Wayland_Surface *ews = NULL;
+ E_Wayland_Input *input = NULL;
+ Eina_List *l = NULL;
+
+ /* try to cast data to our surface structure */
+ if (!(ews = data)) return;
+
+ /* if this surface is not visible, get out */
+ if (!ews->mapped) return;
+
+ /* loop the list of inputs */
+ EINA_LIST_FOREACH(_e_wl_comp->seats, l, input)
+ {
+ /* set keyboard focus */
+ wl_keyboard_set_focus(input->wl.seat.keyboard, NULL);
+
+ /* end any keyboard grabs */
+ wl_keyboard_end_grab(input->wl.seat.keyboard);
+ }
+}
+
+static void
+_e_wl_shell_shell_surface_cb_mouse_in(void *data, Evas_Object *obj
EINA_UNUSED, void *event EINA_UNUSED)
+{
+ E_Wayland_Surface *ews = NULL;
+ struct wl_pointer *ptr = NULL;
+
+ /* try to cast data to our surface structure */
+ if (!(ews = data)) return;
+
+ /* if this surface is not visible, get out */
+ if (!ews->mapped) return;
+
+ /* if (!ews->input) return; */
+
+ /* try to get the pointer from this input */
+ if ((ptr = _e_wl_comp->input->wl.seat.pointer))
+// if ((ptr = ews->input->wl.seat.pointer))
+ {
+ /* if the mouse entered this surface and it is not the current surface
*/
+ if (&ews->wl.surface != ptr->current)
+ {
+ const struct wl_pointer_grab_interface *grab;
+
+ /* set this surface as the current */
+ grab = ptr->grab->interface;
+ ptr->current = &ews->wl.surface;
+
+ /* send a pointer focus event */
+ grab->focus(ptr->grab, &ews->wl.surface,
+ ptr->current_x, ptr->current_y);
+ }
+ }
+}
+
+static void
+_e_wl_shell_shell_surface_cb_mouse_out(void *data, Evas_Object *obj
EINA_UNUSED, void *event EINA_UNUSED)
+{
+ E_Wayland_Surface *ews = NULL;
+ struct wl_pointer *ptr = NULL;
+
+ /* try to cast data to our surface structure */
+ if (!(ews = data)) return;
+
+ /* if (!ews->input) return; */
+
+ /* try to get the pointer from this input */
+ if ((ptr = _e_wl_comp->input->wl.seat.pointer))
+// if ((ptr = ews->input->wl.seat.pointer))
+ {
+ /* if we have a pointer grab and this is the currently focused surface
*/
+ if ((ptr->grab) && (ptr->focus == ptr->current))
+ return;
+
+ /* set pointer focus */
+ ptr->current = NULL;
+
+ /* NB: Ideally, we should call this function to tell the
+ * pointer that nothing has focus, HOWEVER, when we do
+ * it breaks re-entrant focus of some wayland clients:
+ *
+ * NB: I sent a patch for this already to the wayland devs */
+ wl_pointer_set_focus(ptr, NULL, 0, 0);
+ }
+}
+
+static void
+_e_wl_shell_shell_surface_cb_mouse_move(void *data, Evas_Object *obj
EINA_UNUSED, void *event)
+{
+ E_Wayland_Surface *ews = NULL;
+ Evas_Event_Mouse_Move *ev;
+ struct wl_pointer *ptr = NULL;
+
+ ev = event;
+
+ /* try to cast data to our surface structure */
+ if (!(ews = data)) return;
+
+ /* try to get the pointer from this input */
+ if ((ptr = _e_wl_comp->input->wl.seat.pointer))
+// if ((ptr = ews->input->wl.seat.pointer))
+ {
+ ptr->x = wl_fixed_from_int(ev->cur.output.x);
+ ptr->y = wl_fixed_from_int(ev->cur.output.y);
+
+ ptr->current_x = ptr->x;
+ ptr->current_y = ptr->y;
+ ptr->grab->x = ptr->x;
+ ptr->grab->y = ptr->y;
+
+ /* send this mouse movement to wayland */
+ ptr->grab->interface->motion(ptr->grab, ev->timestamp,
+ ptr->grab->x, ptr->grab->y);
+ }
+}
+
/* shell surface interface functions */
static void
_e_wl_shell_shell_surface_cb_pong(struct wl_client *client EINA_UNUSED, struct
wl_resource *resource, unsigned int serial)
@@ -717,4 +895,3 @@ _e_wl_shell_shell_surface_cb_class_set(struct wl_client
*client EINA_UNUSED, str
ecore_evas_name_class_set(ews->ee, ewss->title, ewss->clas);
}
}
-
--
------------------------------------------------------------------------------
Precog is a next-generation analytics platform capable of advanced
analytics on semi-structured data. The platform includes APIs for building
apps and a phenomenal toolset for data science. Developers can use
our toolset for easy data analysis & visualization. Get a free account!
http://www2.precog.com/precogplatform/slashdotnewsletter