From: devilhorns Date: Mon, 16 Jan 2012 19:10:33 +0000 (+0000) Subject: Ecore_Wayland: When handling wayland interfaces (during startup), we X-Git-Tag: 2.0_alpha~86^2~18 X-Git-Url: http://review.tizen.org/git/?a=commitdiff_plain;h=2b45850eab69243bb70333f1383bc2d7b798f25f;p=framework%2Fuifw%2Fecore.git Ecore_Wayland: When handling wayland interfaces (during startup), we cannot depend on the order in which the interfaces are given to us, so we cannot create the data_device until we have both the input device and the data_device_manager. Fix that. Add more dnd code (not complete yet because frankly, the way Wayland handles dnd & selection code is crappy, stupid, and difficult to implement). git-svn-id: svn+ssh://svn.enlightenment.org/var/svn/e/trunk/ecore@67247 7cbeb6ba-43b4-40fd-8cce-4c39aea84d33 --- diff --git a/src/lib/ecore_wayland/Ecore_Wayland.h b/src/lib/ecore_wayland/Ecore_Wayland.h index edb1356..fdf6314 100644 --- a/src/lib/ecore_wayland/Ecore_Wayland.h +++ b/src/lib/ecore_wayland/Ecore_Wayland.h @@ -110,7 +110,7 @@ EAPI void ecore_wl_sync(void); EAPI void ecore_wl_pointer_xy_get(int *x, int *y); EAPI Ecore_Wl_Drag_Source *ecore_wl_drag_source_create(int hotspot_x, int hotspot_y, int offset_x, int offset_y, const char *mimetype, unsigned int timestamp, void *data); -EAPI void ecore_wl_drag_start(Ecore_Wl_Drag_Source *source, struct wl_surface *surface); +EAPI void ecore_wl_drag_start(Ecore_Wl_Drag_Source *source, struct wl_surface *surface, struct wl_buffer *buffer); EAPI void ecore_wl_drag_stop(void); EAPI extern int ECORE_WL_EVENT_MOUSE_IN; diff --git a/src/lib/ecore_wayland/ecore_wl.c b/src/lib/ecore_wayland/ecore_wl.c index e18bd3a..f62503b 100644 --- a/src/lib/ecore_wayland/ecore_wl.c +++ b/src/lib/ecore_wayland/ecore_wl.c @@ -42,15 +42,15 @@ static void _ecore_wl_cb_handle_touch_up(void *data __UNUSED__, struct wl_input_ static void _ecore_wl_cb_handle_touch_motion(void *data __UNUSED__, struct wl_input_device *dev __UNUSED__, uint32_t timestamp, int32_t id, int32_t x, int32_t y); static void _ecore_wl_cb_handle_touch_frame(void *data __UNUSED__, struct wl_input_device *dev __UNUSED__); static void _ecore_wl_cb_handle_touch_cancel(void *data __UNUSED__, struct wl_input_device *dev __UNUSED__); -static void _ecore_wl_cb_source_target(void *data, struct wl_data_source *source, const char *mime_type); +static void _ecore_wl_cb_source_target(void *data, struct wl_data_source *source __UNUSED__, const char *mime_type __UNUSED__); static void _ecore_wl_cb_source_send(void *data, struct wl_data_source *source, const char *mime_type, int32_t fd); -static void _ecore_wl_cb_source_cancelled(void *data, struct wl_data_source *source); +static void _ecore_wl_cb_source_cancelled(void *data, struct wl_data_source *source __UNUSED__); static void _ecore_wl_cb_source_offer(void *data, struct wl_data_offer *offer __UNUSED__, const char *type); static void _ecore_wl_cb_data_offer(void *data, struct wl_data_device *data_dev, uint32_t id); -static void _ecore_wl_cb_data_enter(void *data, struct wl_data_device *data_dev, uint32_t timestamp, struct wl_surface *surface, int32_t x, int32_t y, struct wl_data_offer *offer); -static void _ecore_wl_cb_data_leave(void *data, struct wl_data_device *data_dev __UNUSED__); -static void _ecore_wl_cb_data_motion(void *data, struct wl_data_device *data_dev, uint32_t timestamp, int32_t x, int32_t y); -static void _ecore_wl_cb_data_drop(void *data, struct wl_data_device *data_dev); +static void _ecore_wl_cb_data_enter(void *data __UNUSED__, struct wl_data_device *data_dev, uint32_t timestamp, struct wl_surface *surface, int32_t x, int32_t y, struct wl_data_offer *offer); +static void _ecore_wl_cb_data_leave(void *data __UNUSED__, struct wl_data_device *data_dev); +static void _ecore_wl_cb_data_motion(void *data __UNUSED__, struct wl_data_device *data_dev, uint32_t timestamp, int32_t x, int32_t y); +static void _ecore_wl_cb_data_drop(void *data __UNUSED__, struct wl_data_device *data_dev); static void _ecore_wl_cb_data_selection(void *data, struct wl_data_device *data_dev, struct wl_data_offer *offer); static void _ecore_wl_mouse_move_send(uint32_t timestamp); @@ -340,8 +340,10 @@ ecore_wl_drag_source_create(int hotspot_x, int hotspot_y, int offset_x, int offs } EAPI void -ecore_wl_drag_start(Ecore_Wl_Drag_Source *source, struct wl_surface *surface) +ecore_wl_drag_start(Ecore_Wl_Drag_Source *source, struct wl_surface *surface, struct wl_buffer *buffer) { + source->buffer = buffer; + wl_data_device_start_drag(source->data_dev, source->data_source, surface, source->timestamp); } @@ -429,12 +431,6 @@ _ecore_wl_cb_disp_handle_global(struct wl_display *disp, uint32_t id, const char wl_display_bind(_ecore_wl_disp, id, &wl_input_device_interface); wl_input_device_add_listener(_ecore_wl_input_dev, &_ecore_wl_input_listener, NULL); - - _ecore_wl_data_dev = - wl_data_device_manager_get_data_device(_ecore_wl_data_manager, - _ecore_wl_input_dev); - wl_data_device_add_listener(_ecore_wl_data_dev, - &_ecore_wl_data_listener, NULL); } else if (!strcmp(interface, "wl_data_device_manager")) { @@ -442,6 +438,15 @@ _ecore_wl_cb_disp_handle_global(struct wl_display *disp, uint32_t id, const char wl_display_bind(_ecore_wl_disp, id, &wl_data_device_manager_interface); } + + if ((_ecore_wl_input_dev) && (_ecore_wl_data_manager) && (!_ecore_wl_data_dev)) + { + _ecore_wl_data_dev = + wl_data_device_manager_get_data_device(_ecore_wl_data_manager, + _ecore_wl_input_dev); + wl_data_device_add_listener(_ecore_wl_data_dev, + &_ecore_wl_data_listener, NULL); + } } static int @@ -826,35 +831,59 @@ _ecore_wl_cb_handle_touch_cancel(void *data __UNUSED__, struct wl_input_device * } static void -_ecore_wl_cb_source_target(void *data, struct wl_data_source *source, const char *mime_type) +_ecore_wl_cb_source_target(void *data, struct wl_data_source *source __UNUSED__, const char *mime_type __UNUSED__) { - /* Ecore_Wl_Drag_Source *source; */ + Ecore_Wl_Drag_Source *s; LOGFN(__FILE__, __LINE__, __FUNCTION__); - /* if (!(source = data)) return; */ - -// wl_data_device_set_user_data(data_dev, source); + printf("Ecore_Wl Source Target\n"); + if (!(s = data)) return; + printf("\tHave Drag Source\n"); - /* create a surface & buffer to represent the dragging object */ - /* attach buffer to the surface */ - /* attach to device */ + /* FIXME: buffer here should really be the mouse cursor buffer */ + wl_data_device_attach(s->data_dev, s->timestamp, s->buffer, + s->hotspot_x, s->hotspot_y); } static void _ecore_wl_cb_source_send(void *data, struct wl_data_source *source, const char *mime_type, int32_t fd) { + Ecore_Wl_Drag_Source *s; + LOGFN(__FILE__, __LINE__, __FUNCTION__); + + printf("Ecore_Wl Source Send\n"); + if (!(s = data)) return; + printf("\tHave Drag Source\n"); + + /* FIXME: write message to fd */ + + /* NB: Wayland really sucks in this regard. Why should selection stuff + * require an 'fd' ?? */ } static void -_ecore_wl_cb_source_cancelled(void *data, struct wl_data_source *source) +_ecore_wl_cb_source_cancelled(void *data, struct wl_data_source *source __UNUSED__) { - /* raise this to ecore_evas so the surface/buffer - * of the drag can be destroyed */ + Ecore_Wl_Drag_Source *s; + + LOGFN(__FILE__, __LINE__, __FUNCTION__); /* The cancelled event usually means source is no longer in use by * the drag (or selection). */ + + printf("Ecore_Wl Source Cancel\n"); + if (!(s = data)) return; + printf("\tHave Drag Source\n"); + + /* FIXME: raise this to ecore_evas so the surface/buffer + * of the drag can be destroyed */ + + if (s->data_source) wl_data_source_destroy(s->data_source); + s->data_source = NULL; + + free(s); } static void @@ -871,8 +900,6 @@ _ecore_wl_cb_data_offer(void *data, struct wl_data_device *data_dev, uint32_t id { Ecore_Wl_Dnd_Source *source; - /* data being offered. Could be dnd, or selection */ - /* create a new 'data offer' structure and setup a listener for it */ if (!(source = calloc(1, sizeof(Ecore_Wl_Dnd_Source)))) return; @@ -880,43 +907,87 @@ _ecore_wl_cb_data_offer(void *data, struct wl_data_device *data_dev, uint32_t id source->data = data; source->refs = 1; - /* NB: This will need to change when Wayland has typesafe wrappers for this */ + /* FIXME: This will need to change when Wayland has typesafe wrappers for this */ source->offer = (struct wl_data_offer *) wl_proxy_create_for_id((struct wl_proxy *)data_dev, id, &wl_data_offer_interface); -// wl_data_device_set_user_data(data_dev, source); + wl_data_device_set_user_data(data_dev, source); wl_data_offer_add_listener(source->offer, &_ecore_wl_offer_listener, source); } static void -_ecore_wl_cb_data_enter(void *data, struct wl_data_device *data_dev, uint32_t timestamp, struct wl_surface *surface, int32_t x, int32_t y, struct wl_data_offer *offer) +_ecore_wl_cb_data_enter(void *data __UNUSED__, struct wl_data_device *data_dev, uint32_t timestamp, struct wl_surface *surface, int32_t x, int32_t y, struct wl_data_offer *offer) { + Ecore_Wl_Dnd_Source *source; + if (!(source = wl_data_device_get_user_data(data_dev))) return; + + /* TODO: maybe set pointer focus here ?? */ + + source->timestamp = timestamp; } static void -_ecore_wl_cb_data_leave(void *data __UNUSED__, struct wl_data_device *data_dev __UNUSED__) +_ecore_wl_cb_data_leave(void *data __UNUSED__, struct wl_data_device *data_dev) { + Ecore_Wl_Dnd_Source *source; + + if (!(source = wl_data_device_get_user_data(data_dev))) return; + + /* destroy drag offer */ + wl_data_offer_destroy(source->offer); + while (eina_array_count(source->types)) + free(eina_array_pop(source->types)); + + eina_array_free(source->types); + free(source); + + wl_data_device_set_user_data(data_dev, NULL); } static void -_ecore_wl_cb_data_motion(void *data, struct wl_data_device *data_dev, uint32_t timestamp, int32_t x, int32_t y) +_ecore_wl_cb_data_motion(void *data __UNUSED__, struct wl_data_device *data_dev, uint32_t timestamp, int32_t x, int32_t y) { + Ecore_Wl_Dnd_Source *source; + if (!(source = wl_data_device_get_user_data(data_dev))) return; + /* TODO: Here we should raise motion events for dragging */ } static void -_ecore_wl_cb_data_drop(void *data, struct wl_data_device *data_dev) +_ecore_wl_cb_data_drop(void *data __UNUSED__, struct wl_data_device *data_dev) { + Ecore_Wl_Dnd_Source *source; + + if (!(source = wl_data_device_get_user_data(data_dev))) return; + + /* TODO: Raise event for drop */ + wl_data_offer_accept(source->offer, source->timestamp, NULL); +// eina_array_data_get(source->types, 0)); } static void _ecore_wl_cb_data_selection(void *data, struct wl_data_device *data_dev, struct wl_data_offer *offer) { + Ecore_Wl_Dnd_Source *source; + + printf("Ecore_Wl Data Selection\n"); + if ((source = wl_data_device_get_user_data(data_dev))) + { + /* destroy old source */ + wl_data_offer_destroy(source->offer); + while (eina_array_count(source->types)) + free(eina_array_pop(source->types)); + + eina_array_free(source->types); + free(source); + + wl_data_device_set_user_data(data_dev, NULL); + } } static void diff --git a/src/lib/ecore_wayland/ecore_wl_private.h b/src/lib/ecore_wayland/ecore_wl_private.h index 6c12f57..eec5ffe 100644 --- a/src/lib/ecore_wayland/ecore_wl_private.h +++ b/src/lib/ecore_wayland/ecore_wl_private.h @@ -51,6 +51,7 @@ typedef struct _Ecore_Wl_Dnd_Source Eina_Array *types; + uint32_t timestamp; void *data; } Ecore_Wl_Dnd_Source; @@ -63,12 +64,14 @@ typedef struct _Ecore_Wl_Dnd_Target Eina_Array *types; + uint32_t timestamp; void *data; } Ecore_Wl_Dnd_Target; struct _Ecore_Wl_Drag_Source { struct wl_data_device *data_dev; + struct wl_buffer *buffer; int32_t hotspot_x, hotspot_y; int32_t offset_x, offset_y;