aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorNeil <nyamatongwe@gmail.com>2019-03-28 08:17:18 +1100
committerNeil <nyamatongwe@gmail.com>2019-03-28 08:17:18 +1100
commit87ad00ce89284e66fc818ce60c8109bbfa047329 (patch)
treeb0d5948b7b0f682f87503e91d6e1f0001491c64b
parent722d1571f6e9b76b00095e33525f9775a12414a4 (diff)
downloadscintilla-mirror-87ad00ce89284e66fc818ce60c8109bbfa047329.tar.gz
Bug [#2087]. Fix flicker when inserting primary selection on GTK.
-rw-r--r--doc/ScintillaHistory.html4
-rw-r--r--gtk/ScintillaGTK.cxx68
-rw-r--r--gtk/ScintillaGTK.h4
3 files changed, 48 insertions, 28 deletions
diff --git a/doc/ScintillaHistory.html b/doc/ScintillaHistory.html
index 381dc4ecd..6f08fe033 100644
--- a/doc/ScintillaHistory.html
+++ b/doc/ScintillaHistory.html
@@ -571,6 +571,10 @@
Implement high-priority idle on Win32 to make redraw smoother and more efficient.
</li>
<li>
+ Fix flicker when inserting primary selection on GTK.
+ <a href="https://sourceforge.net/p/scintilla/bugs/2087/">Bug #2087</a>.
+ </li>
+ <li>
Avoid potential long hangs with idle styling for huge documents on Cocoa and GTK.
</li>
<ul>
diff --git a/gtk/ScintillaGTK.cxx b/gtk/ScintillaGTK.cxx
index f213c0097..ccf2498fa 100644
--- a/gtk/ScintillaGTK.cxx
+++ b/gtk/ScintillaGTK.cxx
@@ -1262,37 +1262,47 @@ void ScintillaGTK::Copy() {
}
}
-void ScintillaGTK::Paste() {
- atomSought = atomUTF8;
- GtkClipboard *clipBoard =
- gtk_widget_get_clipboard(GTK_WIDGET(PWidget(wMain)), atomClipboard);
- if (clipBoard == nullptr)
- return;
+namespace {
- // helper class for the asynchronous paste not to risk calling in a destroyed ScintillaGTK
- class Helper : GObjectWatcher {
- ScintillaGTK *sci;
+// Helper class for the asynchronous paste not to risk calling in a destroyed ScintillaGTK
- void Destroyed() override {
- sci = nullptr;
- }
+class SelectionReceiver : GObjectWatcher {
+ ScintillaGTK *sci;
- public:
- Helper(ScintillaGTK *sci_) :
- GObjectWatcher(G_OBJECT(PWidget(sci_->wMain))),
- sci(sci_) {
- }
+ void Destroyed() override {
+ sci = nullptr;
+ }
- static void ClipboardReceived(GtkClipboard *, GtkSelectionData *selection_data, gpointer data) {
- Helper *self = static_cast<Helper *>(data);
- if (self->sci) {
- self->sci->ReceivedSelection(selection_data);
- }
- delete self;
+public:
+ SelectionReceiver(ScintillaGTK *sci_) :
+ GObjectWatcher(G_OBJECT(sci_->MainObject())),
+ sci(sci_) {
+ }
+
+ static void ClipboardReceived(GtkClipboard *, GtkSelectionData *selection_data, gpointer data) {
+ SelectionReceiver *self = static_cast<SelectionReceiver *>(data);
+ if (self->sci) {
+ self->sci->ReceivedSelection(selection_data);
}
- };
+ delete self;
+ }
+};
+
+}
+
+void ScintillaGTK::RequestSelection(GdkAtom atomSelection) {
+ atomSought = atomUTF8;
+ GtkClipboard *clipBoard =
+ gtk_widget_get_clipboard(GTK_WIDGET(PWidget(wMain)), atomSelection);
+ if (clipBoard) {
+ gtk_clipboard_request_contents(clipBoard, atomSought,
+ SelectionReceiver::ClipboardReceived,
+ new SelectionReceiver(this));
+ }
+}
- gtk_clipboard_request_contents(clipBoard, atomSought, Helper::ClipboardReceived, new Helper(this));
+void ScintillaGTK::Paste() {
+ RequestSelection(atomClipboard);
}
void ScintillaGTK::CreateCallTipWindow(PRectangle rc) {
@@ -1423,6 +1433,10 @@ void ScintillaGTK::GetGtkSelectionText(GtkSelectionData *selectionData, Selectio
}
}
+GObject *ScintillaGTK::MainObject() const noexcept {
+ return G_OBJECT(PWidget(wMain));
+}
+
void ScintillaGTK::ReceivedSelection(GtkSelectionData *selection_data) {
try {
if ((SelectionOfGSD(selection_data) == atomClipboard) ||
@@ -1737,9 +1751,7 @@ gint ScintillaGTK::PressThis(GdkEventButton *event) {
sel.Clear();
SetSelection(pos, pos);
- atomSought = atomUTF8;
- gtk_selection_convert(GTK_WIDGET(PWidget(wMain)), GDK_SELECTION_PRIMARY,
- atomSought, event->time);
+ RequestSelection(GDK_SELECTION_PRIMARY);
} else if (event->button == 3) {
if (!PointInSelection(pt))
SetEmptySelection(PositionFromLocation(pt));
diff --git a/gtk/ScintillaGTK.h b/gtk/ScintillaGTK.h
index 501903b42..c175192f9 100644
--- a/gtk/ScintillaGTK.h
+++ b/gtk/ScintillaGTK.h
@@ -127,13 +127,17 @@ private:
int KeyDefault(int key, int modifiers) override;
void CopyToClipboard(const SelectionText &selectedText) override;
void Copy() override;
+ void RequestSelection(GdkAtom atomSelection);
void Paste() override;
void CreateCallTipWindow(PRectangle rc) override;
void AddToPopUp(const char *label, int cmd = 0, bool enabled = true) override;
bool OwnPrimarySelection();
void ClaimSelection() override;
void GetGtkSelectionText(GtkSelectionData *selectionData, SelectionText &selText);
+public: // Public for SelectionReceiver
+ GObject *MainObject() const noexcept;
void ReceivedSelection(GtkSelectionData *selection_data);
+private:
void ReceivedDrop(GtkSelectionData *selection_data);
static void GetSelection(GtkSelectionData *selection_data, guint info, SelectionText *text);
void StoreOnClipboard(SelectionText *clipText);