Blame SOURCES/fltk-1_v3.3.x-clipboard-xfixes.patch

ceac5b
diff -ur fltk-1.3.0r9619.org/configh.in fltk-1.3.0r9619/configh.in
ceac5b
--- fltk-1.3.0r9619.org/configh.in	2011-10-04 11:21:47.000000000 +0200
ceac5b
+++ fltk-1.3.0r9619/configh.in	2012-06-18 16:14:05.012277003 +0200
ceac5b
@@ -108,6 +108,14 @@
ceac5b
 #define USE_XDBE HAVE_XDBE
ceac5b
 
ceac5b
 /*
ceac5b
+ * HAVE_XFIXES:
ceac5b
+ *
ceac5b
+ * Do we have the X fixes extension?
ceac5b
+ */
ceac5b
+
ceac5b
+#define HAVE_XFIXES 0
ceac5b
+
ceac5b
+/*
ceac5b
  * __APPLE_QUARTZ__:
ceac5b
  *
ceac5b
  * All Apple implementations are now based on Quartz and Cocoa,
ceac5b
diff -ur fltk-1.3.0r9619.org/configure.in fltk-1.3.0r9619/configure.in
ceac5b
--- fltk-1.3.0r9619.org/configure.in	2012-06-18 16:13:38.744017220 +0200
ceac5b
+++ fltk-1.3.0r9619/configure.in	2012-06-18 16:14:05.013277050 +0200
ceac5b
@@ -999,6 +999,16 @@
ceac5b
 		LIBS="-lXext $LIBS")
ceac5b
 	fi
ceac5b
 
ceac5b
+	dnl Check for the Xfixes extension unless disabled...
ceac5b
+        AC_ARG_ENABLE(xfixes, [  --enable-xfixes       turn on Xfixes support [default=yes]])
ceac5b
+
ceac5b
+	if test x$enable_xfixes != xno; then
ceac5b
+	    AC_CHECK_HEADER(X11/extensions/Xfixes.h, AC_DEFINE(HAVE_XFIXES),,
ceac5b
+	        [#include <X11/Xlib.h>])
ceac5b
+	    AC_CHECK_LIB(Xfixes, XFixesQueryExtension,
ceac5b
+		LIBS="-lXfixes $LIBS")
ceac5b
+	fi
ceac5b
+
ceac5b
 	dnl Check for overlay visuals...
ceac5b
 	AC_PATH_PROG(XPROP, xprop)
ceac5b
 	AC_CACHE_CHECK(for X overlay visuals, ac_cv_have_overlay,
ceac5b
diff -ur fltk-1.3.0r9619.org/src/Fl_x.cxx fltk-1.3.0r9619/src/Fl_x.cxx
ceac5b
--- fltk-1.3.0r9619.org/src/Fl_x.cxx	2012-06-18 16:13:38.749017460 +0200
ceac5b
+++ fltk-1.3.0r9619/src/Fl_x.cxx	2012-06-18 16:13:24.000000000 +0200
ceac5b
@@ -53,6 +53,12 @@
ceac5b
 static int randrEventBase;                  // base of RandR-defined events
ceac5b
 #endif
ceac5b
 
ceac5b
+#  ifdef HAVE_XFIXES
ceac5b
+#  include <X11/extensions/Xfixes.h>
ceac5b
+static int xfixes_event_base = 0;
ceac5b
+static bool have_xfixes = false;
ceac5b
+#  endif
ceac5b
+
ceac5b
 static Fl_Xlib_Graphics_Driver fl_xlib_driver;
ceac5b
 static Fl_Display_Device fl_xlib_display(&fl_xlib_driver);
ceac5b
 Fl_Display_Device *Fl_Display_Device::_display = &fl_xlib_display;// the platform display
ceac5b
@@ -197,6 +203,14 @@
ceac5b
     Fl::handle(FL_MOVE, fl_xmousewin);
ceac5b
   }
ceac5b
 #endif
ceac5b
+
ceac5b
+#ifdef HAVE_XFIXES
ceac5b
+  int error_base;
ceac5b
+  if (XFixesQueryExtension(fl_display, &xfixes_event_base, &error_base))
ceac5b
+    have_xfixes = true;
ceac5b
+  else
ceac5b
+    have_xfixes = false;
ceac5b
+#endif
ceac5b
 }
ceac5b
 
ceac5b
 // these pointers are set by the Fl::lock() function:
ceac5b
@@ -917,6 +931,10 @@
ceac5b
 static void poll_clipboard_owner(void) {
ceac5b
   Window xid;
ceac5b
 
ceac5b
+  // No polling needed with Xfixes
ceac5b
+  if (have_xfixes)
ceac5b
+    return;
ceac5b
+
ceac5b
   // No one is interested, so no point polling
ceac5b
   if (fl_clipboard_notify_empty())
ceac5b
     return;
ceac5b
@@ -955,10 +973,12 @@
ceac5b
 
ceac5b
   timestamp = clipboard ? &clipboard_timestamp : &primary_timestamp;
ceac5b
 
ceac5b
-  // Initial scan, just store the value
ceac5b
-  if (*timestamp == (Time)-1) {
ceac5b
-    *timestamp = time;
ceac5b
-    return;
ceac5b
+  if (!have_xfixes) {
ceac5b
+    // Initial scan, just store the value
ceac5b
+    if (*timestamp == (Time)-1) {
ceac5b
+      *timestamp = time;
ceac5b
+      return;
ceac5b
+    }
ceac5b
   }
ceac5b
 
ceac5b
   // Same selection
ceac5b
@@ -978,10 +998,12 @@
ceac5b
     primary_timestamp = -1;
ceac5b
     clipboard_timestamp = -1;
ceac5b
   } else {
ceac5b
-    poll_clipboard_owner();
ceac5b
+    if (!have_xfixes) {
ceac5b
+      poll_clipboard_owner();
ceac5b
 
ceac5b
-    if (!Fl::has_timeout(clipboard_timeout))
ceac5b
-      Fl::add_timeout(0.5, clipboard_timeout);
ceac5b
+      if (!Fl::has_timeout(clipboard_timeout))
ceac5b
+        Fl::add_timeout(0.5, clipboard_timeout);
ceac5b
+    }
ceac5b
   }
ceac5b
 }
ceac5b
 
ceac5b
@@ -1780,6 +1802,25 @@
ceac5b
     }
ceac5b
   }
ceac5b
 
ceac5b
+#ifdef HAVE_XFIXES
ceac5b
+  switch (xevent.type - xfixes_event_base) {
ceac5b
+  case XFixesSelectionNotify: {
ceac5b
+    // Someone feeding us bogus events?
ceac5b
+    if (!have_xfixes)
ceac5b
+      return true;
ceac5b
+
ceac5b
+    XFixesSelectionNotifyEvent *selection_notify = (XFixesSelectionNotifyEvent *)&xevent;
ceac5b
+
ceac5b
+    if ((selection_notify->selection == XA_PRIMARY) && !fl_i_own_selection[0])
ceac5b
+      handle_clipboard_timestamp(0, selection_notify->selection_timestamp);
ceac5b
+    else if ((selection_notify->selection == CLIPBOARD) && !fl_i_own_selection[1])
ceac5b
+      handle_clipboard_timestamp(1, selection_notify->selection_timestamp);
ceac5b
+
ceac5b
+    return true;
ceac5b
+    }
ceac5b
+  }
ceac5b
+#endif
ceac5b
+
ceac5b
   return Fl::handle(event, window);
ceac5b
 }
ceac5b
 
ceac5b
@@ -2100,6 +2141,16 @@
ceac5b
     XChangeProperty(fl_display, xp->xid, net_wm_type, XA_ATOM, 32, PropModeReplace, (unsigned char*)&net_wm_type_kind, 1);
ceac5b
   }
ceac5b
 
ceac5b
+#ifdef HAVE_XFIXES
ceac5b
+  // register for clipboard change notifications
ceac5b
+  if (have_xfixes && !win->parent()) {
ceac5b
+    XFixesSelectSelectionInput(fl_display, xp->xid, XA_PRIMARY,
ceac5b
+                               XFixesSetSelectionOwnerNotifyMask);
ceac5b
+    XFixesSelectSelectionInput(fl_display, xp->xid, CLIPBOARD,
ceac5b
+                               XFixesSetSelectionOwnerNotifyMask);
ceac5b
+  }
ceac5b
+#endif
ceac5b
+
ceac5b
   XMapWindow(fl_display, xp->xid);
ceac5b
   if (showit) {
ceac5b
     win->set_visible();