void QWaylandDataDevice::data_device_motion(uint32_t time, wl_fixed_t x, wl_fixed_t y) { Q_UNUSED(time); QDrag *drag = static_cast<QWaylandDrag *>(QGuiApplicationPrivate::platformIntegration()->drag())->currentDrag(); if (!drag && !m_dragOffer) return; m_dragPoint = QPoint(wl_fixed_to_int(x), wl_fixed_to_int(y)); QMimeData *dragData; Qt::DropActions supportedActions; if (drag) { dragData = drag->mimeData(); supportedActions = drag->supportedActions(); } else { dragData = m_dragOffer->mimeData(); supportedActions = Qt::CopyAction | Qt::MoveAction | Qt::LinkAction; } QPlatformDragQtResponse response = QWindowSystemInterface::handleDrag(m_dragWindow, dragData, m_dragPoint, supportedActions); if (drag) { static_cast<QWaylandDrag *>(QGuiApplicationPrivate::platformIntegration()->drag())->setResponse(response); } else { if (response.isAccepted()) { wl_data_offer_accept(m_dragOffer->object(), m_enterSerial, m_dragOffer->firstFormat().toUtf8().constData()); } else { wl_data_offer_accept(m_dragOffer->object(), m_enterSerial, 0); } } }
void QWaylandDataDevice::data_device_enter(uint32_t serial, wl_surface *surface, wl_fixed_t x, wl_fixed_t y, wl_data_offer *id) { m_enterSerial = serial; m_dragWindow = QWaylandWindow::fromWlSurface(surface)->window(); m_dragPoint = QPoint(wl_fixed_to_int(x), wl_fixed_to_int(y)); QDrag *drag = static_cast<QWaylandDrag *>(QGuiApplicationPrivate::platformIntegration()->drag())->currentDrag(); QMimeData *dragData; Qt::DropActions supportedActions; if (drag) { dragData = drag->mimeData(); supportedActions = drag->supportedActions(); } else { m_dragOffer.reset(static_cast<QWaylandDataOffer *>(wl_data_offer_get_user_data(id))); if (m_dragOffer) { dragData = m_dragOffer->mimeData(); supportedActions = Qt::CopyAction | Qt::MoveAction | Qt::LinkAction; } } const QPlatformDragQtResponse &response = QWindowSystemInterface::handleDrag(m_dragWindow, dragData, m_dragPoint, supportedActions); if (drag) { static_cast<QWaylandDrag *>(QGuiApplicationPrivate::platformIntegration()->drag())->setResponse(response); } else { if (response.isAccepted()) { wl_data_offer_accept(m_dragOffer->object(), m_enterSerial, m_dragOffer->firstFormat().toUtf8().constData()); } else { wl_data_offer_accept(m_dragOffer->object(), m_enterSerial, 0); } } }
static void data_device_handle_enter(void *data, struct wl_data_device *wl_data_device, uint32_t serial, struct wl_surface *surface, wl_fixed_t x, wl_fixed_t y, struct wl_data_offer *id) { SDL_WaylandDataDevice *data_device = data; SDL_bool has_mime = SDL_FALSE; uint32_t dnd_action = WL_DATA_DEVICE_MANAGER_DND_ACTION_NONE; data_device->drag_serial = serial; if (id != NULL) { data_device->drag_offer = wl_data_offer_get_user_data(id); /* TODO: SDL Support more mime types */ has_mime = Wayland_data_offer_has_mime( data_device->drag_offer, FILE_MIME); /* If drag_mime is NULL this will decline the offer */ wl_data_offer_accept(id, serial, (has_mime == SDL_TRUE) ? FILE_MIME : NULL); /* SDL only supports "copy" style drag and drop */ if (has_mime == SDL_TRUE) { dnd_action = WL_DATA_DEVICE_MANAGER_DND_ACTION_COPY; } wl_data_offer_set_actions(data_device->drag_offer->offer, dnd_action, dnd_action); } }
static void data_device_handle_enter(void *data, struct wl_data_device *wl_data_device, uint32_t serial, struct wl_surface *surface, wl_fixed_t x, wl_fixed_t y, struct wl_data_offer *id) { struct vo_wayland_state *wl = data; if (wl->input.offer != id) MP_FATAL(wl, "Fatal dnd error (Please report this issue)\n"); wl_data_offer_accept(id, serial, "text/uri-list"); }
void _gdk_wayland_display_convert_selection (GdkDisplay *display, GdkWindow *requestor, GdkAtom selection, GdkAtom target, guint32 time) { GdkWaylandSelection *wayland_selection = gdk_wayland_display_get_selection (display); SelectionBuffer *buffer_data; if (!wayland_selection->offer) { GdkEvent *event; event = gdk_event_new (GDK_SELECTION_NOTIFY); event->selection.window = g_object_ref (requestor); event->selection.send_event = FALSE; event->selection.selection = selection; event->selection.target = target; event->selection.property = GDK_NONE; event->selection.time = GDK_CURRENT_TIME; event->selection.requestor = g_object_ref (requestor); gdk_event_put (event); gdk_event_free (event); return; } wl_data_offer_accept (wayland_selection->offer, _gdk_wayland_display_get_serial (GDK_WAYLAND_DISPLAY (display)), gdk_atom_name (target)); buffer_data = g_hash_table_lookup (wayland_selection->selection_buffers, target); if (buffer_data) selection_buffer_add_requestor (buffer_data, requestor); else { GInputStream *stream = NULL; int pipe_fd[2], natoms = 0; GdkAtom *atoms = NULL; if (target == gdk_atom_intern_static_string ("TARGETS")) { gint i = 0; GList *l; natoms = g_list_length (wayland_selection->targets); atoms = g_new0 (GdkAtom, natoms); for (l = wayland_selection->targets; l; l = l->next) atoms[i++] = l->data; } else { g_unix_open_pipe (pipe_fd, FD_CLOEXEC, NULL); wl_data_offer_receive (wayland_selection->offer, gdk_atom_name (target), pipe_fd[1]); stream = g_unix_input_stream_new (pipe_fd[0], TRUE); close (pipe_fd[1]); } buffer_data = selection_buffer_new (stream, selection, target); selection_buffer_add_requestor (buffer_data, requestor); if (stream) g_object_unref (stream); if (atoms) { /* Store directly the local atoms */ selection_buffer_append_data (buffer_data, atoms, natoms * sizeof (GdkAtom)); g_free (atoms); } g_hash_table_insert (wayland_selection->selection_buffers, GDK_ATOM_TO_POINTER (target), buffer_data); } if (!buffer_data->stream) selection_buffer_notify (buffer_data); }
void _gdk_wayland_display_convert_selection (GdkDisplay *display, GdkWindow *requestor, GdkAtom selection, GdkAtom target, guint32 time) { GdkWaylandSelection *wayland_selection = gdk_wayland_display_get_selection (display); const SelectionData *selection_data; SelectionBuffer *buffer_data; gpointer offer; gchar *mimetype; GList *target_list; selection_data = selection_lookup_offer_by_atom (wayland_selection, selection); if (!selection_data) return; offer = gdk_wayland_selection_get_offer (display, selection); target_list = gdk_wayland_selection_get_targets (display, selection); if (!offer || target == gdk_atom_intern_static_string ("DELETE")) { emit_empty_selection_notify (requestor, selection, target); return; } mimetype = gdk_atom_name (target); if (target != gdk_atom_intern_static_string ("TARGETS")) { if (!g_list_find (target_list, GDK_ATOM_TO_POINTER (target))) { emit_empty_selection_notify (requestor, selection, target); return; } if (selection != atoms[ATOM_PRIMARY]) wl_data_offer_accept (offer, _gdk_wayland_display_get_serial (GDK_WAYLAND_DISPLAY (display)), mimetype); } buffer_data = g_hash_table_lookup (selection_data->buffers, target); if (buffer_data) selection_buffer_add_requestor (buffer_data, requestor); else { GInputStream *stream = NULL; int pipe_fd[2], natoms = 0; GdkAtom *targets = NULL; if (target == gdk_atom_intern_static_string ("TARGETS")) { gint i = 0; GList *l; natoms = g_list_length (target_list); targets = g_new0 (GdkAtom, natoms); for (l = target_list; l; l = l->next) targets[i++] = l->data; } else { g_unix_open_pipe (pipe_fd, FD_CLOEXEC, NULL); if (selection == atoms[ATOM_PRIMARY]) gtk_primary_selection_offer_receive (offer, mimetype, pipe_fd[1]); else wl_data_offer_receive (offer, mimetype, pipe_fd[1]); stream = g_unix_input_stream_new (pipe_fd[0], TRUE); close (pipe_fd[1]); } buffer_data = selection_buffer_new (stream, selection, target); selection_buffer_add_requestor (buffer_data, requestor); if (stream) g_object_unref (stream); if (targets) { /* Store directly the local atoms */ selection_buffer_append_data (buffer_data, targets, natoms * sizeof (GdkAtom)); g_free (targets); } g_hash_table_insert (selection_data->buffers, GDK_ATOM_TO_POINTER (target), buffer_data); } if (!buffer_data->stream) selection_buffer_notify (buffer_data); g_free (mimetype); }