Bug 1869043 assert that graph set access is main thread only r=padenot
[gecko.git] / widget / gtk / AsyncGtkClipboardRequest.cpp
blob75801c698daa2fb2dce81b48f31cb80ebbf40fd5
1 /* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
2 /* vim: set ts=4 et sw=2 tw=80: */
3 /* This Source Code Form is subject to the terms of the Mozilla Public
4 * License, v. 2.0. If a copy of the MPL was not distributed with this
5 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
7 #include "AsyncGtkClipboardRequest.h"
9 namespace mozilla {
11 AsyncGtkClipboardRequest::AsyncGtkClipboardRequest(ClipboardDataType aDataType,
12 int32_t aWhichClipboard,
13 const char* aMimeType) {
14 GtkClipboard* clipboard =
15 gtk_clipboard_get(GetSelectionAtom(aWhichClipboard));
16 mRequest = MakeUnique<Request>(aDataType);
18 switch (aDataType) {
19 case ClipboardDataType::Data:
20 LOGCLIP(" getting DATA MIME %s\n", aMimeType);
21 gtk_clipboard_request_contents(clipboard,
22 gdk_atom_intern(aMimeType, FALSE),
23 OnDataReceived, mRequest.get());
24 break;
25 case ClipboardDataType::Text:
26 LOGCLIP(" getting TEXT\n");
27 gtk_clipboard_request_text(clipboard, OnTextReceived, mRequest.get());
28 break;
29 case ClipboardDataType::Targets:
30 LOGCLIP(" getting TARGETS\n");
31 gtk_clipboard_request_contents(clipboard,
32 gdk_atom_intern("TARGETS", FALSE),
33 OnDataReceived, mRequest.get());
34 break;
38 void AsyncGtkClipboardRequest::OnDataReceived(GtkClipboard* clipboard,
39 GtkSelectionData* selection_data,
40 gpointer data) {
41 int whichClipboard = GetGeckoClipboardType(clipboard);
42 LOGCLIP("OnDataReceived(%s) callback\n",
43 whichClipboard == nsClipboard::kSelectionClipboard ? "primary"
44 : "clipboard");
45 static_cast<Request*>(data)->Complete(selection_data);
48 void AsyncGtkClipboardRequest::OnTextReceived(GtkClipboard* clipboard,
49 const gchar* text,
50 gpointer data) {
51 int whichClipboard = GetGeckoClipboardType(clipboard);
52 LOGCLIP("OnTextReceived(%s) callback\n",
53 whichClipboard == nsClipboard::kSelectionClipboard ? "primary"
54 : "clipboard");
55 static_cast<Request*>(data)->Complete(text);
58 void AsyncGtkClipboardRequest::Request::Complete(const void* aData) {
59 LOGCLIP("Request::Complete(), aData = %p, timedOut = %d\n", aData, mTimedOut);
61 if (mTimedOut) {
62 delete this;
63 return;
66 mData.emplace();
68 gint dataLength = 0;
69 if (mDataType == ClipboardDataType::Targets ||
70 mDataType == ClipboardDataType::Data) {
71 dataLength = gtk_selection_data_get_length((GtkSelectionData*)aData);
72 } else {
73 dataLength = aData ? strlen((const char*)aData) : 0;
76 // Negative size means no data or data error.
77 if (dataLength <= 0) {
78 LOGCLIP(" zero dataLength, quit.\n");
79 return;
82 switch (mDataType) {
83 case ClipboardDataType::Targets: {
84 LOGCLIP(" getting %d bytes of clipboard targets.\n", dataLength);
85 gint n_targets = 0;
86 GdkAtom* targets = nullptr;
87 if (!gtk_selection_data_get_targets((GtkSelectionData*)aData, &targets,
88 &n_targets) ||
89 !n_targets) {
90 // We failed to get targets
91 return;
93 mData->SetTargets(
94 ClipboardTargets{GUniquePtr<GdkAtom>(targets), uint32_t(n_targets)});
95 break;
97 case ClipboardDataType::Text: {
98 LOGCLIP(" getting %d bytes of text.\n", dataLength);
99 mData->SetText(Span(static_cast<const char*>(aData), dataLength));
100 LOGCLIP(" done, mClipboardData = %p\n", mData->AsSpan().data());
101 break;
103 case ClipboardDataType::Data: {
104 LOGCLIP(" getting %d bytes of data.\n", dataLength);
105 mData->SetData(Span(gtk_selection_data_get_data((GtkSelectionData*)aData),
106 dataLength));
107 LOGCLIP(" done, mClipboardData = %p\n", mData->AsSpan().data());
108 break;
113 AsyncGtkClipboardRequest::~AsyncGtkClipboardRequest() {
114 if (mRequest && mRequest->mData.isNothing()) {
115 mRequest->mTimedOut = true;
116 Unused << mRequest.release();
120 } // namespace mozilla