diff options
author | Tony Crisci <tony@dubstepdish.com> | 2017-11-21 18:09:25 -0500 |
---|---|---|
committer | Tony Crisci <tony@dubstepdish.com> | 2017-11-21 18:09:25 -0500 |
commit | 39e2ea8420e78710906308a17a65b55e9d03dda8 (patch) | |
tree | 2750b12e2270282e9a8c6ddc3155718f4c7f0c8b /xwayland/selection.c | |
parent | 1ada1b7f0bdf048ea3d5f01c6b8eb7badfd97eae (diff) |
xwm: get selection targets
Diffstat (limited to 'xwayland/selection.c')
-rw-r--r-- | xwayland/selection.c | 68 |
1 files changed, 62 insertions, 6 deletions
diff --git a/xwayland/selection.c b/xwayland/selection.c index c458f867..911a3627 100644 --- a/xwayland/selection.c +++ b/xwayland/selection.c @@ -1,3 +1,6 @@ +#define _XOPEN_SOURCE 700 +#include <stdlib.h> +#include <string.h> #include <xcb/xfixes.h> #include <fcntl.h> #include "wlr/util/log.h" @@ -53,11 +56,11 @@ static void data_source_send(struct wlr_data_source *base, if (strcmp(mime_type, "text/plain;charset=utf-8") == 0) { // Get data for the utf8_string target xcb_convert_selection(xwm->xcb_conn, - xwm->selection_window, - xwm->atoms[CLIPBOARD], - xwm->atoms[UTF8_STRING], - xwm->atoms[WL_SELECTION], - XCB_TIME_CURRENT_TIME); + xwm->selection_window, + xwm->atoms[CLIPBOARD], + xwm->atoms[UTF8_STRING], + xwm->atoms[WL_SELECTION], + XCB_TIME_CURRENT_TIME); xcb_flush(xwm->xcb_conn); @@ -71,7 +74,54 @@ static void data_source_cancel(struct wlr_data_source *source) { static void xwm_get_selection_targets(struct wlr_xwm *xwm) { // set the wayland clipboard selection to the copied selection - wlr_log(L_DEBUG, "TODO: GET SELECTION TARGETS"); + + xcb_get_property_cookie_t cookie = xcb_get_property(xwm->xcb_conn, + 1, // delete + xwm->selection_window, + xwm->atoms[WL_SELECTION], + XCB_GET_PROPERTY_TYPE_ANY, + 0, // offset + 4096 //length + ); + + xcb_get_property_reply_t *reply = + xcb_get_property_reply(xwm->xcb_conn, cookie, NULL); + if (reply == NULL) + return; + + if (reply->type != XCB_ATOM_ATOM) { + free(reply); + return; + } + + struct x11_data_source *source = calloc(1, sizeof(struct x11_data_source)); + if (source == NULL) { + free(reply); + return; + } + + wl_signal_init(&source->base.events.destroy); + source->base.accept = data_source_accept; + source->base.send = data_source_send; + source->base.cancel = data_source_cancel; + source->xwm = xwm; + + wl_array_init(&source->base.mime_types); + xcb_atom_t *value = xcb_get_property_value(reply); + for (uint32_t i = 0; i < reply->value_len; i++) { + if (value[i] == xwm->atoms[UTF8_STRING]) { + char **p = wl_array_add(&source->base.mime_types, sizeof *p); + if (p) { + *p = strdup("text/plain;charset=utf-8"); + } + } + } + + wlr_seat_set_selection(xwm->xwayland->seat, &source->base, + wl_display_next_serial(xwm->xwayland->wl_display)); + + free(reply); + } static void xwm_handle_selection_notify(struct wlr_xwm *xwm, @@ -133,6 +183,12 @@ static int xwm_handle_xfixes_selection_notify(struct wlr_xwm *xwm, int xwm_handle_selection_event(struct wlr_xwm *xwm, xcb_generic_event_t *event) { + if (!xwm->xwayland->seat) { + wlr_log(L_DEBUG, "not handling selection events:" + "no seat assigned to xwayland"); + return 0; + } + switch (event->response_type & ~0x80) { case XCB_SELECTION_NOTIFY: xwm_handle_selection_notify(xwm, event); |