diff --git a/fltk/extensions.patch b/fltk/extensions.patch
index 6eebe84..1cb5c74 100644
--- a/fltk/extensions.patch
+++ b/fltk/extensions.patch
@@ -1,4460 +1,4152 @@
-diff -up fltk-1.3.x-r8732/src/Fl_win32.cxx.hwheel fltk-1.3.x-r8732/src/Fl_win32.cxx
---- fltk-1.3.x-r8732/src/Fl_win32.cxx.hwheel	2011-05-21 23:55:59.000000000 +0200
-+++ fltk-1.3.x-r8732/src/Fl_win32.cxx	2011-05-24 13:37:31.109341034 +0200
-@@ -1125,12 +1286,28 @@ static LRESULT CALLBACK WndProc(HWND hWn
-   case WM_MOUSEWHEEL: {
-     static int delta = 0; // running total of all motion
-     delta += (SHORT)(HIWORD(wParam));
-+    Fl::e_dx = 0;
-     Fl::e_dy = -delta / WHEEL_DELTA;
-     delta += Fl::e_dy * WHEEL_DELTA;
-     if (Fl::e_dy) Fl::handle(FL_MOUSEWHEEL, window);
-     return 0;
-   }
- 
-+// This is only defined on Vista and upwards...
-+#ifndef WM_MOUSEHWHEEL
-+#define WM_MOUSEHWHEEL 0x020E
-+#endif
-+
-+  case WM_MOUSEHWHEEL: {
-+    static int delta = 0; // running total of all motion
-+    delta += (SHORT)(HIWORD(wParam));
-+    Fl::e_dy = 0;
-+    Fl::e_dx = delta / WHEEL_DELTA;
-+    delta -= Fl::e_dx * WHEEL_DELTA;
-+    if (Fl::e_dx) Fl::handle(FL_MOUSEWHEEL, window);
-+    return 0;
-+  }
-+
-   case WM_GETMINMAXINFO:
-     Fl_X::i(window)->set_minmax((LPMINMAXINFO)lParam);
-     break;
-diff -up fltk-1.3.x-r8732/src/Fl_x.cxx.hwheel fltk-1.3.x-r8732/src/Fl_x.cxx
---- fltk-1.3.x-r8732/src/Fl_x.cxx.hwheel	2011-05-23 21:40:23.000000000 +0200
-+++ fltk-1.3.x-r8732/src/Fl_x.cxx	2011-05-24 13:36:49.635113914 +0200
-@@ -1441,12 +1608,19 @@ int fl_handle(const XEvent& thisevent)
-   case ButtonPress:
-     Fl::e_keysym = FL_Button + xevent.xbutton.button;
-     set_event_xy();
-+    Fl::e_dx = Fl::e_dy = 0;
-     if (xevent.xbutton.button == Button4) {
-       Fl::e_dy = -1; // Up
-       event = FL_MOUSEWHEEL;
-     } else if (xevent.xbutton.button == Button5) {
-       Fl::e_dy = +1; // Down
-       event = FL_MOUSEWHEEL;
-+    } else if (xevent.xbutton.button == 6) {
-+      Fl::e_dx = -1; // Left
-+      event = FL_MOUSEWHEEL;
-+    } else if (xevent.xbutton.button == 7) {
-+      Fl::e_dx = +1; // Right
-+      event = FL_MOUSEWHEEL;
-     } else {
-       Fl::e_state |= (FL_BUTTON1 << (xevent.xbutton.button-1));
-       event = FL_PUSH;
---- fltk-1.3.x-r8744/src/screen_xywh.cxx.fullscreen	2011-05-26 15:48:00.000000000 +0200
-+++ fltk-1.3.x-r8744/src/screen_xywh.cxx	2011-06-01 14:00:08.256046579 +0200
-@@ -202,81 +202,21 @@ int Fl::screen_count() {
-   \param[in] mx, my the absolute screen position
- */
- void Fl::screen_xywh(int &X, int &Y, int &W, int &H, int mx, int my) {
--  if (num_screens < 0) screen_init();
--
--#ifdef WIN32
--  if (num_screens > 0) {
--    int i;
--
--    for (i = 0; i < num_screens; i ++) {
--      if (mx >= screens[i].left && mx < screens[i].right &&
--	  my >= screens[i].top && my < screens[i].bottom) {
--	X = screens[i].left;
--	Y = screens[i].top;
--	W = screens[i].right - screens[i].left;
--	H = screens[i].bottom - screens[i].top;
--	return;
--      }
--    }
--  }
--  // if all else fails:
--  X = Fl::x();
--  Y = Fl::y();
--  W = Fl::w();
--  H = Fl::h();
--#elif defined(__APPLE__)
--  if (num_screens > 0) {
--    int i;
-+  int screen = 0;
-+  int i;
- 
--    for (i = 0; i < num_screens; i ++) {
--      if (mx >= screens[i].x &&
--	  mx < (screens[i].x + screens[i].width) &&
--	  my >= screens[i].y &&
--	  my < (screens[i].y + screens[i].height)) {
--	X = screens[i].x;
--	Y = screens[i].y;
--	W = screens[i].width;
--	H = screens[i].height;
--	return;
--      }
--    }
--  }
--  // if all else fails:
--  X = Fl::x();
--  Y = Fl::y();
--  W = Fl::w();
--  H = Fl::h();
--#elif HAVE_XINERAMA
--  if (num_screens > 0 && screens) { // screens == NULL if !XineramaIsActive(fl_display)
--    int i;
-+  if (num_screens < 0) screen_init();
- 
--    for (i = 0; i < num_screens; i ++) {
--      if (mx >= screens[i].x_org &&
--	  mx < (screens[i].x_org + screens[i].width) &&
--	  my >= screens[i].y_org &&
--	  my < (screens[i].y_org + screens[i].height)) {
--	X = screens[i].x_org;
--	Y = screens[i].y_org;
--	W = screens[i].width;
--	H = screens[i].height;
--	return;
--      }
-+  for (i = 0; i < num_screens; i ++) {
-+    int sx, sy, sw, sh;
-+    Fl::screen_xywh(sx, sy, sw, sh, i);
-+    if ((mx >= sx) && (mx < (sx+sw)) && (my >= sy) && (my < (sy+sh))) {
-+      screen = i;
-+      break;
-     }
-   }
--  // if all else fails:
--  X = Fl::x();
--  Y = Fl::y();
--  W = Fl::w();
--  H = Fl::h();
--#else
--  (void)mx;
--  (void)my;
--  X = 0;
--  Y = 0;
--  W = DisplayWidth(fl_display, fl_screen);
--  H = DisplayHeight(fl_display, fl_screen);
--#endif // WIN32
- 
-+  screen_xywh(X, Y, W, H, screen);
- }
- 
- /**
-@@ -288,47 +228,51 @@ void Fl::screen_xywh(int &X, int &Y, int
- void Fl::screen_xywh(int &X, int &Y, int &W, int &H, int n) {
-   if (num_screens < 0) screen_init();
- 
-+  if ((n < 0) || (n >= num_screens))
-+    n = 0;
-+
- #ifdef WIN32
--  if (num_screens > 0 && n >= 0 && n < num_screens) {
-+  if (num_screens > 0) {
-     X = screens[n].left;
-     Y = screens[n].top;
-     W = screens[n].right - screens[n].left;
-     H = screens[n].bottom - screens[n].top;
-   } else {
--    X = Fl::x();
--    Y = Fl::y();
--    W = Fl::w();
--    H = Fl::h();
-+    /* Fallback if something is broken... */
-+    X = 0;
-+    Y = 0;
-+    W = GetSystemMetrics(SM_CXSCREEN);
-+    H = GetSystemMetrics(SM_CYSCREEN);
-   }
- #elif defined(__APPLE__)
--  if (num_screens > 0 && n >= 0 && n < num_screens) {
-+  if (num_screens > 0) {
-     X = screens[n].x;
-     Y = screens[n].y;
-     W = screens[n].width;
-     H = screens[n].height;
-   } else {
-+    /* Fallback if something is broken... */
-     X = Fl::x();
-     Y = Fl::y();
-     W = Fl::w();
-     H = Fl::h();
-   }
--#elif HAVE_XINERAMA
--  if (num_screens > 0 && n >= 0 && n < num_screens && screens) {
-+#else
-+#if HAVE_XINERAMA
-+  if (num_screens > 0) {
-     X = screens[n].x_org;
-     Y = screens[n].y_org;
-     W = screens[n].width;
-     H = screens[n].height;
--  } else {
--    X = Fl::x();
--    Y = Fl::y();
--    W = Fl::w();
--    H = Fl::h();
-+  } else
-+#endif // HAVE_XINERAMA
-+  {
-+    /* Fallback if something is broken (or no Xinerama)... */
-+    X = 0;
-+    Y = 0;
-+    W = DisplayWidth(fl_display, fl_screen);
-+    H = DisplayHeight(fl_display, fl_screen);
-   }
--#else
--  X = 0;
--  Y = 0;
--  W = DisplayWidth(fl_display, fl_screen);
--  H = DisplayHeight(fl_display, fl_screen);
- #endif // WIN32
- }
- 
-diff -up fltk-1.3.x-r8659/FL/Fl_Widget.H.kbd-x11 fltk-1.3.x-r8659/FL/Fl_Widget.H
---- fltk-1.3.x-r8659/FL/Fl_Widget.H.kbd-x11	2011-04-24 19:09:41.000000000 +0200
-+++ fltk-1.3.x-r8659/FL/Fl_Widget.H	2011-05-13 13:51:26.307888360 +0200
-@@ -179,6 +179,7 @@ protected:
-         NO_OVERLAY      = 1<<15,  ///< window not using a hardware overlay plane (Fl_Menu_Window)
-         GROUP_RELATIVE  = 1<<16,  ///< position this widget relative to the parent group, not to the window
-         COPIED_TOOLTIP  = 1<<17,  ///< the widget tooltip is internally copied, its destruction is handled by the widget
-+        SIMPLE_KEYBOARD = 1<<18,  ///< the widget wants simple, consistent keypresses and not advanced input (like character composition and CJK input)
-         // (space for more flags)
-         USERFLAG3       = 1<<29,  ///< reserved for 3rd party extensions
-         USERFLAG2       = 1<<30,  ///< reserved for 3rd party extensions
-@@ -784,6 +785,35 @@ public:
-    */
-   void clear_changed() {flags_ &= ~CHANGED;}
- 
-+  /** 
-+      Returns if the widget sees a simplified keyboard model or not.
-+
-+      Normally widgets get a full-featured keyboard model that is geared
-+      towards text input. This includes support for compose sequences and
-+      advanced input methods, commonly used for asian writing system. This
-+      system however has downsides in that extra graphic can be presented
-+      to the user and that a physical key press doesn't correspond directly
-+      to a FLTK event.
-+
-+      Widgets that need a direct correspondence between actual key events
-+      and those seen by the widget can swith to the simplified keyboard
-+      model.
-+
-+     \retval 0 if the widget uses the normal keyboard model
-+     \see set_changed(), clear_changed()
-+   */
-+  unsigned int simple_keyboard() const {return flags_&SIMPLE_KEYBOARD;}
-+
-+  /** Marks a widget to use the simple keyboard model.
-+      \see changed(), clear_changed()
-+   */
-+  void set_simple_keyboard() {flags_ |= SIMPLE_KEYBOARD;}
-+
-+  /** Marks a widget to use the normal keyboard model.
-+      \see changed(), set_changed()
-+   */
-+  void set_normal_keyboard() {flags_ &= ~SIMPLE_KEYBOARD;}
-+
-   /** Gives the widget the keyboard focus.
-       Tries to make this widget be the Fl::focus() widget, by first sending 
-       it an FL_FOCUS event, and if it returns non-zero, setting 
-diff -up fltk-1.3.x-r8659/src/Fl.cxx.kbd-x11 fltk-1.3.x-r8659/src/Fl.cxx
---- fltk-1.3.x-r8659/src/Fl.cxx.kbd-x11	2011-04-11 22:10:02.000000000 +0200
-+++ fltk-1.3.x-r8659/src/Fl.cxx	2011-05-13 13:51:26.308888510 +0200
-@@ -63,6 +63,8 @@ void fl_cleanup_dc_list(void);
- extern double fl_mac_flush_and_wait(double time_to_wait, char in_idle);
- #endif // WIN32
- 
-+extern void fl_update_focus(void);
-+
- //
- // Globals...
- //
-@@ -864,6 +866,8 @@ void Fl::focus(Fl_Widget *o) {
-       fl_oldfocus = p;
-     }
-     e_number = old_event;
-+    // let the platform code do what it needs
-+    fl_update_focus();
-   }
- }
- 
-diff -up fltk-1.3.x-r8659/src/Fl_grab.cxx.kbd-x11 fltk-1.3.x-r8659/src/Fl_grab.cxx
---- fltk-1.3.x-r8659/src/Fl_grab.cxx.kbd-x11	2010-12-18 23:31:01.000000000 +0100
-+++ fltk-1.3.x-r8659/src/Fl_grab.cxx	2011-05-13 13:51:26.309888660 +0200
-@@ -38,6 +38,7 @@
- // override_redirect, it does similar things on WIN32.
- 
- extern void fl_fix_focus(); // in Fl.cxx
-+void fl_update_focus(void);
- 
- #ifdef WIN32
- // We have to keep track of whether we have captured the mouse, since
-@@ -79,6 +80,7 @@ void Fl::grab(Fl_Window* win) {
- #endif
-     }
-     grab_ = win;
-+    fl_update_focus();
-   } else {
-     if (grab_) {
- #ifdef WIN32
-@@ -94,6 +96,7 @@ void Fl::grab(Fl_Window* win) {
-       XFlush(fl_display);
- #endif
-       grab_ = 0;
-+      fl_update_focus();
-       fl_fix_focus();
-     }
-   }
-diff -up fltk-1.3.x-r8659/src/Fl_x.cxx.kbd-x11 fltk-1.3.x-r8659/src/Fl_x.cxx
---- fltk-1.3.x-r8659/src/Fl_x.cxx.kbd-x11	2011-04-27 10:47:00.000000000 +0200
-+++ fltk-1.3.x-r8659/src/Fl_x.cxx	2011-05-13 13:54:28.813284014 +0200
-@@ -300,6 +300,7 @@ XVisualInfo *fl_visual;
- Colormap fl_colormap;
- XIM fl_xim_im = 0;
- XIC fl_xim_ic = 0;
-+Window fl_xim_win = 0;
- char fl_is_over_the_spot = 0;
- static XRectangle status_area;
- 
-@@ -581,6 +582,65 @@ void fl_init_xim() {
-   if(xim_styles) XFree(xim_styles);
- }
- 
-+void fl_xim_deactivate(void);
-+
-+void fl_xim_activate(Window xid)
-+{
-+  if (!fl_xim_im)
-+    return;
-+
-+  // If the focused window has changed, then use the brute force method
-+  // of completely recreating the input context.
-+  if (fl_xim_win != xid) {
-+    fl_xim_deactivate();
-+
-+    fl_new_ic();
-+    fl_xim_win = xid;
-+
-+    XSetICValues(fl_xim_ic,
-+                 XNFocusWindow, fl_xim_win,
-+                 XNClientWindow, fl_xim_win,
-+                 NULL);
-+  }
-+
-+  fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
-+}
-+
-+void fl_xim_deactivate(void)
-+{
-+  if (!fl_xim_ic)
-+    return;
-+
-+  XDestroyIC(fl_xim_ic);
-+  fl_xim_ic = NULL;
-+
-+  fl_xim_win = 0;
-+}
-+
-+extern Fl_Window *fl_xfocus;
-+
-+void fl_update_focus(void)
-+{
-+  Fl_Widget *focus;
-+
-+  focus = Fl::grab();
-+  if (!focus)
-+    focus = Fl::focus();
-+  if (!focus)
-+    return;
-+
-+  if (focus->simple_keyboard()) {
-+    fl_xim_deactivate();
-+  } else {
-+    // fl_xfocus should always be set if something has focus, but let's
-+    // play it safe
-+    if (!fl_xfocus || !fl_xid(fl_xfocus))
-+      return;
-+
-+    fl_xim_activate(fl_xid(fl_xfocus));
-+  }
-+}
-+
- void fl_open_display() {
-   if (fl_display) return;
- 
-@@ -864,10 +924,9 @@ int fl_handle(const XEvent& thisevent)
-   XEvent xevent = thisevent;
-   fl_xevent = &thisevent;
-   Window xid = xevent.xany.window;
--  static Window xim_win = 0;
- 
-   if (fl_xim_ic && xevent.type == DestroyNotify &&
--        xid != xim_win && !fl_find(xid))
-+        xid != fl_xim_win && !fl_find(xid))
-   {
-     XIM xim_im;
-     xim_im = XOpenIM(fl_display, NULL, NULL, NULL);
-@@ -882,48 +941,10 @@ int fl_handle(const XEvent& thisevent)
-     return 0;
-   }
- 
--  if (fl_xim_ic && (xevent.type == FocusIn))
--  {
--#define POOR_XIM
--#ifdef POOR_XIM
--        if (xim_win != xid)
--        {
--                xim_win  = xid;
--                XDestroyIC(fl_xim_ic);
--                fl_xim_ic = NULL;
--                fl_new_ic();
--                XSetICValues(fl_xim_ic,
--                                XNFocusWindow, xevent.xclient.window,
--                                XNClientWindow, xid,
--                                NULL);
--        }
--        fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
--#else
--    if (Fl::first_window() && Fl::first_window()->modal()) {
--      Window x  = fl_xid(Fl::first_window());
--      if (x != xim_win) {
--        xim_win  = x;
--        XSetICValues(fl_xim_ic,
--                        XNFocusWindow, xim_win,
--                        XNClientWindow, xim_win,
--                        NULL);
--        fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
--      }
--    } else if (xim_win != xid && xid) {
--      xim_win = xid;
--      XSetICValues(fl_xim_ic,
--                        XNFocusWindow, xevent.xclient.window,
--                        XNClientWindow, xid,
--                        //XNFocusWindow, xim_win,
--                        //XNClientWindow, xim_win,
--                        NULL);
--      fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
--    }
--#endif
--  }
--
--  if ( XFilterEvent((XEvent *)&xevent, 0) )
--      return(1);
-+  if (fl_xim_ic) {
-+    if (XFilterEvent((XEvent *)&xevent, 0))
-+      return 1;
-+  }
- 
-   switch (xevent.type) {
- 
-@@ -1248,15 +1269,15 @@ int fl_handle(const XEvent& thisevent)
-         //static XComposeStatus compose;
-         len = XLookupString((XKeyEvent*)&(xevent.xkey),
-                              buffer, buffer_len, &keysym, 0/*&compose*/);
--        if (keysym && keysym < 0x400) { // a character in latin-1,2,3,4 sets
--          // force it to type a character (not sure if this ever is needed):
--          // if (!len) {buffer[0] = char(keysym); len = 1;}
--          len = fl_utf8encode(XKeysymToUcs(keysym), buffer);
--          if (len < 1) len = 1;
--          // ignore all effects of shift on the keysyms, which makes it a lot
--          // easier to program shortcuts and is Windoze-compatible:
--          keysym = XKeycodeToKeysym(fl_display, keycode, 0);
--        }
-+        // XLookupString() is only defined to return Latin-1 (although it
-+        // often gives you more). To be safe, use our own lookups based on
-+        // keysym.
-+        len = fl_utf8encode(XKeysymToUcs(keysym), buffer);
-+        if (len < 1)
-+          len = 1;
-+        // ignore all effects of shift on the keysyms, which makes it a lot
-+        // easier to program shortcuts and is Windoze-compatable:
-+        keysym = XKeycodeToKeysym(fl_display, keycode, 0);
-       }
-       // MRS: Can't use Fl::event_state(FL_CTRL) since the state is not
-       //      set until set_event_xy() is called later...
-diff -up fltk-1.3.x-r8659/src/xutf8/imKStoUCS.c.kbd-x11 fltk-1.3.x-r8659/src/xutf8/imKStoUCS.c
---- fltk-1.3.x-r8659/src/xutf8/imKStoUCS.c.kbd-x11	2009-03-13 23:43:43.000000000 +0100
-+++ fltk-1.3.x-r8659/src/xutf8/imKStoUCS.c	2011-05-13 13:51:26.311888960 +0200
-@@ -266,6 +266,12 @@ static unsigned short const keysym_to_un
-     0x20a8, 0x20a9, 0x20aa, 0x20ab, 0x20ac                          /* 0x20a8-0x20af */
- };
- 
-+static unsigned short const keysym_to_unicode_fe50_fe60[] = {
-+    0x0300, 0x0301, 0x0302, 0x0303, 0x0304, 0x0306, 0x0307, 0x0308, /* 0xfe50-0xfe57 */
-+    0x030a, 0x030b, 0x030c, 0x0327, 0x0328, 0x1da5, 0x3099, 0x309a, /* 0xfe58-0xfe5f */
-+    0x0323                                                          /* 0xfe60-0xfe67 */
-+};
-+
- unsigned int
- KeySymToUcs4(KeySym keysym)
- {
-@@ -315,6 +321,8 @@ KeySymToUcs4(KeySym keysym)
- 	return keysym_to_unicode_1e9f_1eff[keysym - 0x1e9f];
-     else if (keysym > 0x209f && keysym < 0x20ad)
- 	return keysym_to_unicode_20a0_20ac[keysym - 0x20a0];
-+    else if (keysym > 0xfe4f && keysym < 0xfe61)
-+	return keysym_to_unicode_fe50_fe60[keysym - 0xfe50];
-     else 
- 	return 0;
- }
-diff -up fltk-1.3.x-r8617/src/Fl_win32.cxx.kbd-win32 fltk-1.3.x-r8617/src/Fl_win32.cxx
---- fltk-1.3.x-r8617/src/Fl_win32.cxx.kbd-win32	2011-04-18 22:47:32.000000000 +0200
-+++ fltk-1.3.x-r8617/src/Fl_win32.cxx	2011-05-13 13:43:12.131708663 +0200
-@@ -98,6 +98,8 @@ FL_EXPORT Fl_Graphics_Driver *fl_graphic
- Fl_Surface_Device* Fl_Surface_Device::_surface = (Fl_Surface_Device*)&fl_gdi_display; // the current target surface of graphics operations
- Fl_Display_Device *Fl_Display_Device::_display = &fl_gdi_display; // the platform display
- 
-+bool use_simple_keyboard = false;
-+
- // dynamic wsock dll handling api:
- #if defined(__CYGWIN__) && !defined(SOCKET)
- # define SOCKET int
-@@ -131,6 +133,8 @@ static HMODULE get_wsock_mod() {
-  * size and link dependencies.
+*** fltk-1.3.0/CMakeLists.txt	2011-01-06 04:24:58.000000000 -0600
+--- fltk/CMakeLists.txt	2011-06-22 23:01:51.000000000 -0500
+***************
+*** 62,65 ****
+--- 62,66 ----
+     set(HAVE_DIRENT_H 1)
+     set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -framework Cocoa")
++    set(CMAKE_EXE_LINKER_FLAGS "${CMAKE_EXE_LINKER_FLAGS} -framework Carbon")
+  endif(APPLE)
+  
+*** fltk-1.3.0/FL/Enumerations.H	2011-05-21 16:55:59.000000000 -0500
+--- fltk/FL/Enumerations.H	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 293,297 ****
+        following FL_PASTE event.
+     */
+!   FL_DND_RELEASE	= 23
+  };
+  
+--- 293,302 ----
+        following FL_PASTE event.
+     */
+!   FL_DND_RELEASE	= 23,
+! 
+!   /** The fullscreen state of the window has changed
+!    */
+!   FL_FULLSCREEN         = 24
+! 
+  };
+  
+***************
+*** 875,907 ****
+  /** The following constants define the mouse cursors that are available in FLTK.
+  
+!     The double-headed arrows are bitmaps provided by FLTK on X, the others
+!     are provided by system-defined cursors.
+  
+      \todo enum Fl_Cursor needs maybe an image.
   */
- static HMODULE s_imm_module = 0;
-+typedef BOOL (WINAPI* flTypeImmAssociateContextEx)(HWND, HIMC, DWORD);
-+static flTypeImmAssociateContextEx flImmAssociateContextEx = 0;
- typedef HIMC (WINAPI* flTypeImmGetContext)(HWND);
- static flTypeImmGetContext flImmGetContext = 0;
- typedef BOOL (WINAPI* flTypeImmSetCompositionWindow)(HIMC, LPCOMPOSITIONFORM);
-@@ -146,6 +150,7 @@ static HMODULE get_imm_module() {
-     if (!s_imm_module)
-       Fl::fatal("FLTK Lib Error: IMM32.DLL file not found!\n\n"
-         "Please check your input method manager library accessibility.");
-+    flImmAssociateContextEx = (flTypeImmAssociateContextEx)GetProcAddress(s_imm_module, "ImmAssociateContextEx");
-     flImmGetContext = (flTypeImmGetContext)GetProcAddress(s_imm_module, "ImmGetContext");
-     flImmSetCompositionWindow = (flTypeImmSetCompositionWindow)GetProcAddress(s_imm_module, "ImmSetCompositionWindow");
-     flImmReleaseContext = (flTypeImmReleaseContext)GetProcAddress(s_imm_module, "ImmReleaseContext");
-@@ -424,7 +429,12 @@ int fl_wait(double time_to_wait) {
-         }
-       }
- 
--      TranslateMessage(&fl_msg);
-+      // Don't bother with key to character translation as we do
-+      // it manually for simpley keyboard widgets. In fact, calling
-+      // TranslateMessage() just makes it more difficult as it sets
-+      // a bunch of internal state.
-+      if (!use_simple_keyboard)
-+        TranslateMessage(&fl_msg);
-       DispatchMessageW(&fl_msg);
-       have_message = PeekMessageW(&fl_msg, NULL, 0, 0, PM_REMOVE);
-     }
-@@ -649,6 +659,49 @@ void fl_get_codepage()
-   }
- }
- 
-+void fl_update_focus(void)
-+{
-+  Fl_Widget *focus;
-+  Fl_Window *win;
-+
-+  get_imm_module();
-+
-+  focus = Fl::grab();
-+  if (!focus)
-+    focus = Fl::focus();
-+  if (!focus)
-+    return;
-+
-+  // Grabs are special in that events are sent to the first
-+  // available window
-+  if (focus == Fl::grab())
-+    win = Fl::first_window();
-+  else {
-+    win = focus->as_window();
-+    if (!win)
-+      win = focus->window();
-+  }
-+
-+  if (!win) {
-+    Fl::warning("Cannot find window for widget receiving focus");
-+    return;
-+  }
-+
-+  // No Win32 window created yet
-+  if (!Fl_X::i(win) || !fl_xid(win))
-+    return;
-+
-+  if (focus->simple_keyboard()) {
-+    use_simple_keyboard = true;
-+    if (flImmGetContext(fl_xid(win)) != 0)
-+      flImmAssociateContextEx(fl_xid(win), 0, 0);
-+  } else {
-+    use_simple_keyboard = false;
-+    if (flImmGetContext(fl_xid(win)) == 0)
-+      flImmAssociateContextEx(fl_xid(win), 0, IACE_DEFAULT);
-+  }
-+}
-+
- HWND fl_capture;
- 
- static int mouse_event(Fl_Window *window, int what, int button,
-@@ -778,6 +831,27 @@ static int ms2fltk(int vk, int extended)
-   return extended ? extendedlut[vk] : vklut[vk];
- }
- 
-+static xchar msdead2fltk(xchar in)
-+{
-+  switch (in) {
-+  case 0x0060:      // GRAVE ACCENT
-+    return 0x0300;  // COMBINING GRAVE ACCENT
-+  case 0x00b4:      // ACUTE ACCENT
-+    return 0x0301;  // COMBINING ACUTE ACCENT
-+  case 0x005e:      // CIRCUMFLEX ACCENT
-+    return 0x0302;  // COMBINING CIRCUMFLEX ACCENT
-+  case 0x007e:      // TILDE
-+    return 0x0303;  // COMBINING TILDE
-+  case 0x00a8:      // DIAERESIS
-+    return 0x0308;  // COMBINING DIAERESIS
-+  // FIXME: Windows dead key behaviour isn't documented and I don't have
-+  //        any more keyboards to test with...
-+  }
-+
-+  // hope that Windows gave us something proper to begin with
-+  return in;
-+}
-+
- #if USE_COLORMAP
- extern HPALETTE fl_select_palette(void); // in fl_color_win32.cxx
- #endif
-@@ -839,6 +913,8 @@ static LRESULT CALLBACK WndProc(HWND hWn
-   //fl_msg.pt = ???
-   //fl_msg.lPrivate = ???
- 
-+  MSG fl_orig_msg = fl_msg;
-+
-   Fl_Window *window = fl_find(hWnd);
- 
-   if (window) switch (uMsg) {
-@@ -1018,23 +1094,82 @@ static LRESULT CALLBACK WndProc(HWND hWn
-     if (GetKeyState(VK_SCROLL)) state |= FL_SCROLL_LOCK;
-     Fl::e_state = state;
-     static char buffer[1024];
--    if (uMsg == WM_CHAR || uMsg == WM_SYSCHAR) {
- 
-+    if (use_simple_keyboard) {
-+      BYTE keystate[256];
-+      WCHAR wbuf[8];
-+      int ret;
-+
-+      // I'm not sure if we ever get WM_CHAR (& friends) without an initial
-+      // WM_KEYDOWN (& friends), but if we do then we should not send such
-+      // side band events to simple keyboard widgets.
-+      if ((fl_orig_msg.message != WM_KEYDOWN) &&
-+          (fl_orig_msg.message != WM_SYSKEYDOWN) &&
-+          (fl_orig_msg.message != WM_KEYUP) &&
-+          (fl_orig_msg.message != WM_SYSKEYUP))
-+        break;
-+
-+      GetKeyboardState(keystate);
-+
-+      // Pressing Ctrl wreaks havoc with the symbol lookup, so turn that off.
-+      // But AltGr shows up as Ctrl+Alt in Windows, so keep Ctrl if Alt is
-+      // active.
-+      if (!(keystate[VK_MENU] & (1<<31)))
-+        keystate[VK_CONTROL] = keystate[VK_LCONTROL] = keystate[VK_RCONTROL] = 0;
-+
-+      // We cannot inspect or modify Windows' internal state of the keyboard
-+      // so we have to try to infer information from ToUnicode() and wedge
-+      // things into a known state.
-+      for (int i = 0;i < 2;i++) {
-+        ret = ToUnicode(fl_orig_msg.wParam, 0, keystate, wbuf,
-+                        sizeof(wbuf)/sizeof(wbuf[0]), 0);
-+
-+        // No symbol for this key (or unexpected length)
-+        if ((ret == 0) || (ret < -1)) {
-+          buffer[0] = 0;
-+          Fl::e_length = 0;
-+          break;
-+        }
-+
-+        // A dead key. Convert this to a Unicode combining character so
-+        // that the application can tell the difference between dead and
-+        // normal keys.
-+        if (ret == -1) {
-+          xchar u = (xchar) msdead2fltk(wbuf[0]);
-+          Fl::e_length = fl_utf8fromwc(buffer, 1024, &u, 1);
-+          buffer[Fl::e_length] = 0;
-+          break;
-+        }
-+
-+        // If we have two characters (or more) from ToUnicode(), that's
-+        // an invalid sequence. One character chould mean a proper symbol,
-+        // or it could mean a composed one. In both cases we need to call
-+        // ToUnicode() again to get something sane.
-+        if (i == 0)
-+          continue;
-+
-+        // We should now have something sane. Give whatever we have to the
-+        // application.
-+        Fl::e_length = fl_utf8fromwc(buffer, 1024, wbuf, ret);
-+        buffer[Fl::e_length] = 0;
-+      }
-+    } else if (uMsg == WM_CHAR || uMsg == WM_SYSCHAR) {
-       xchar u = (xchar) wParam;
- //    Fl::e_length = fl_unicode2utf(&u, 1, buffer);
-       Fl::e_length = fl_utf8fromwc(buffer, 1024, &u, 1);
-       buffer[Fl::e_length] = 0;
-+    } else {
-+      buffer[0] = 0;
-+      Fl::e_length = 0;
-+    }
- 
--
--    } else if (Fl::e_keysym >= FL_KP && Fl::e_keysym <= FL_KP_Last) {
--      if (state & FL_NUM_LOCK) {
--        // Convert to regular keypress...
--	buffer[0] = Fl::e_keysym-FL_KP;
--	Fl::e_length = 1;
--      } else {
--        // Convert to special keypress...
--	buffer[0] = 0;
--	Fl::e_length = 0;
-+    // The keypad area is a bit odd in that we need to change the keysym
-+    // to properly indicate what the user meant, unlike other keys where
-+    // we normally change the text and keep keysym stable.
-+    if (Fl::e_keysym >= FL_KP && Fl::e_keysym <= FL_KP_Last) {
-+      // The initial mapping tables give us a keysym that corresponds to
-+      // numlock being on, so we only do something when it is off.
-+      if (!(state & FL_NUM_LOCK)) {
- 	switch (Fl::e_keysym) {
- 	  case FL_KP + '0' :
- 	    Fl::e_keysym = FL_Insert;
-@@ -1066,30 +1201,10 @@ static LRESULT CALLBACK WndProc(HWND hWn
- 	  case FL_KP + '.' :
- 	    Fl::e_keysym = FL_Delete;
- 	    break;
--	  case FL_KP + '/' :
--	  case FL_KP + '*' :
--	  case FL_KP + '-' :
--	  case FL_KP + '+' :
--	    buffer[0] = Fl::e_keysym-FL_KP;
--	    Fl::e_length = 1;
--	    break;
- 	}
-       }
--    } else if ((lParam & (1<<31))==0) {
--#ifdef FLTK_PREVIEW_DEAD_KEYS
--      if ((lParam & (1<<24))==0) { // clear if dead key (always?)
--        xchar u = (xchar) wParam;
--        Fl::e_length = fl_utf8fromwc(buffer, 1024, &u, 1);
--        buffer[Fl::e_length] = 0;
--      } else { // set if "extended key" (never printable?)
--        buffer[0] = 0;
--        Fl::e_length = 0;
--      }
--#else
--      buffer[0] = 0;
--      Fl::e_length = 0;
--#endif
-     }
-+
-     Fl::e_text = buffer;
-     if (lParam & (1<<31)) { // key up events.
-       if (Fl::handle(FL_KEYUP, window)) return 0;
-diff -up fltk-1.3.x-r8695/configure.in.kbd-osx fltk-1.3.x-r8695/configure.in
---- fltk-1.3.x-r8695/configure.in.kbd-osx	2011-03-06 17:54:58.000000000 +0100
-+++ fltk-1.3.x-r8695/configure.in	2011-05-20 12:16:49.545510571 +0200
-@@ -874,6 +874,8 @@ case $uname_GUI in
-     Darwin*)
-         # MacOS X uses Cocoa for graphics.
-         LIBS="$LIBS -framework Cocoa"
-+        # And some Carbon for keyboard handling
-+        LIBS="$LIBS -framework Carbon"
- 
- 	if test x$have_pthread = xyes; then
- 	    AC_DEFINE(HAVE_PTHREAD)
-diff -up fltk-1.3.x-r8695/src/Fl_cocoa.mm.kbd-osx fltk-1.3.x-r8695/src/Fl_cocoa.mm
---- fltk-1.3.x-r8695/src/Fl_cocoa.mm.kbd-osx	2011-05-15 14:34:31.000000000 +0200
-+++ fltk-1.3.x-r8695/src/Fl_cocoa.mm	2011-05-20 12:21:01.376320373 +0200
-@@ -61,6 +61,7 @@ extern "C" {
- #include <stdarg.h>
- 
- #import <Cocoa/Cocoa.h>
-+#import <Carbon/Carbon.h>
- 
- #ifndef NSINTEGER_DEFINED // appears with 10.5 in NSObjCRuntime.h
- #if defined(__LP64__) && __LP64__
-@@ -124,6 +125,8 @@ static Fl_Window* send_motion;
- extern Fl_Window* fl_xmousewin;
- #endif
- 
-+bool use_simple_keyboard = false;
-+
- enum { FLTKTimerEvent = 1, FLTKDataReadyEvent };
- 
- 
-@@ -140,6 +143,39 @@ void fl_set_status(int x, int y, int w, 
- {
- }
- 
-+// Undocumented voodoo. Taken from Mozilla.
-+#define ENABLE_ROMAN_KYBDS_ONLY -23
-+
-+void fl_update_focus(void)
-+{
-+  Fl_Widget *focus;
-+
-+  focus = Fl::grab();
-+  if (!focus)
-+    focus = Fl::focus();
-+  if (!focus)
-+    return;
-+
-+  if (focus->simple_keyboard())
-+    use_simple_keyboard = true;
-+  else
-+    use_simple_keyboard = false;
-+
-+  // Force a "Roman" or "ASCII" keyboard, which both the Mozilla and
-+  // Safari people seem to think implies turning off advanced IME stuff
-+  // (see nsTSMManager::SyncKeyScript in Mozilla and enableSecureTextInput
-+  // in Safari/Webcore). Should be good enough for us then...
-+#if (MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5)
-+  CFArrayRef inputSources = TISCreateASCIICapableInputSourceList();
-+  TSMSetDocumentProperty(TSMGetActiveDocument(),
-+                         kTSMDocumentEnabledInputSourcesPropertyTag,
-+                         sizeof(CFArrayRef), &inputSources);
-+  CFRelease(inputSources);
-+#else
-+  KeyScript(use_simple_keyboard ? ENABLE_ROMAN_KYBDS_ONLY : smKeyEnableKybds);
-+#endif  
-+}
-+
- /*
-  * Mac keyboard lookup table
-  * See also the inverse converter vktab in Fl_get_key_mac.cxx
-@@ -842,6 +878,25 @@ static void cocoaMouseHandler(NSEvent *t
- }
- @end
- 
-+static const char* cocoaDead2FLTK(const char *in)
-+{
-+  if (strcmp(in, "\140") == 0)      // GRAVE ACCENT
-+    return "\314\200";              // COMBINING GRAVE ACCENT
-+  if (strcmp(in, "\302\264") == 0)  // ACUTE ACCENT
-+    return "\314\201";              // COMBINING ACUTE ACCENT
-+  if (strcmp(in, "\136") == 0)      // CIRCUMFLEX ACCENT
-+    return "\314\202";              // COMBINING CIRCUMFLEX ACCENT
-+  if (strcmp(in, "\176") == 0)      // TILDE
-+    return "\314\203";              // COMBINING TILDE
-+  if (strcmp(in, "\302\250") == 0)  // DIAERESIS
-+    return "\314\210";              // COMBINING DIAERESIS
-+  // FIXME: OS X dead key behaviour isn't documented and I don't have
-+  //        any more keyboards to test with...
-+
-+  // hope that OS X gave us something proper to begin with
-+  return in;
-+}
-+
- /*
- Handle cocoa keyboard events
- Events during a character composition sequence:
-@@ -1701,8 +1756,13 @@ static void  q_set_window_title(NSWindow
-       break;
-     }
-   }
-+  // Don't send cmd-<key> to interpretKeyEvents because it beeps.
-   if (!no_text_key && !(Fl::e_state & FL_META) ) {
--    // Don't send cmd-<key> to interpretKeyEvents because it beeps.
-+    // The simple keyboard model will ignore insertText, so we need to grab
-+    // the symbol directly from the event. Note that we still use setMarkedText.
-+    if (use_simple_keyboard)
-+      [FLView prepareEtext:[theEvent charactersIgnoringModifiers]];
-+
-     // Then we can let the OS have a stab at it and see if it thinks it
-     // should result in some text
-     NSText *edit = [[theEvent window]  fieldEditor:YES forObject:nil];
-@@ -1879,21 +1939,30 @@ static void  q_set_window_title(NSWindow
-   //NSLog(@"insertText: received=%@",received);
- 
-   if (!in_key_event) fl_lock_function();
-+
-+  // Simple keyboard widgets do not want these side channel inputs.
-+  if (use_simple_keyboard)
-+    goto end;
-+
-   [FLView prepareEtext:received];
-+
-   // We can get called outside of key events (e.g. from the character
--  // palette). Transform such actions to FL_PASTE events.
-+  // palette). We need to fake our own key event at that point.
-   if (!in_key_event) {
-     Fl_Window *target = [(FLWindow*)[self window] getFl_Window];
--    Fl::handle(FL_PASTE, target);
-+    Fl::e_keysym = Fl::e_original_keysym = 0;
-+    Fl::handle(FL_KEYDOWN, target);
-     // for some reason, the window does not redraw until the next mouse move or button push
-     // sending a 'redraw()' or 'awake()' does not solve the issue!
-     Fl::flush();
-   }
-+
-+end:
-   if (!in_key_event) fl_unlock_function();
- }
- 
- - (void)setMarkedText:(id)aString selectedRange:(NSRange)newSelection  {
--  NSString *received;
-+  NSString *received, *current, *aggregate;
-   if (newSelection.location == 0) {
-     [self unmarkText];
-     return;
-@@ -1904,11 +1973,47 @@ static void  q_set_window_title(NSWindow
-     received = (NSString*)aString;
-   }
-   //NSLog(@"setMarkedText: %@ %d %d",received,newSelection.location,newSelection.length);
-+
-+  fl_lock_function();
-+
-+  // Simple keyboard widgets generally do not want these side channel
-+  // inputs, but we have no other way of getting dead keys so we make
-+  // an exception in that case.
-+  if (use_simple_keyboard) {
-+    if (in_key_event && (Fl::e_length == 0)) {
-+      [FLView prepareEtext:received];
-+
-+      Fl::e_text = (char*)cocoaDead2FLTK(Fl::e_text);
-+      Fl::e_length = strlen(Fl::e_text);
-+    }
-+    goto end;
-+  }
-+
-   // This code creates the OS X behaviour of seeing dead keys as things
-   // are being composed.
-+  //
-+  // Note: The concatenation thing is because of how OS X deals with
-+  //       invalid sequences. At that point it will spit out one call
-+  //       to insertText with the now aborted sequence, and one new
-+  //       call to setMarkedText with the new sequence. Since we want
-+  //       both to be visible, we need to concatenate.
-   next_compose_length = newSelection.location;
--  [FLView prepareEtext:received];
--  //NSLog(@"Fl::e_text=%@ Fl::e_length=%d next_compose_length=%d", received, Fl::e_length, next_compose_length);
-+  current = [NSString stringWithUTF8String:Fl::e_text];
-+  aggregate = [current stringByAppendingString:received];
-+
-+  [FLView prepareEtext:aggregate];
-+  //NSLog(@"Fl::e_text=%@ Fl::e_length=%d next_compose_length=%d", aggregate, Fl::e_length, next_compose_length);
-+
-+  // We can get called outside of key events (e.g. from the character
-+  // palette). We need to fake our own key event at that point.
-+  if (!in_key_event) {
-+    Fl_Window *target = [(FLWindow*)[self window] getFl_Window];
-+    Fl::e_keysym = Fl::e_original_keysym = 0;
-+    Fl::handle(FL_KEYDOWN, target);
-+  }
-+
-+end:
-+  fl_unlock_function();
- }
- 
- - (void)unmarkText {
-diff -up fltk-1.3.x-r8659/FL/Fl.H.orig fltk-1.3.x-r8659/FL/Fl.H
---- fltk-1.3.x-r8659/FL/Fl.H.orig	2011-05-17 16:25:56.671744548 +0200
-+++ fltk-1.3.x-r8659/FL/Fl.H	2011-05-17 16:26:05.709101536 +0200
-@@ -108,6 +108,9 @@ typedef int (*Fl_Args_Handler)(int argc,
-     \see Fl::event_dispatch(Fl_Event_Dispatch) */
- typedef int (*Fl_Event_Dispatch)(int event, Fl_Window *w);
- 
-+/** Signature of add_clipboard_notify functions passed as parameters */
-+typedef void (*Fl_Clipboard_Notify_Handler)(int source, void *data);
-+
- /** @} */ /* group callback_functions */
- 
- 
-@@ -744,6 +747,19 @@ public:
-   */
-   static void paste(Fl_Widget &receiver, int source /*=0*/); // platform dependent
-   /**
-+  FLTK will call the registered callback whenever there is a change to the
-+  selection buffer or the clipboard. The source argument indicates which
-+  of the two has changed. Only changes by other applications are reported.
-+  \note Some systems require polling to monitor the clipboard and may
-+  therefore have some delay in detecting changes.
-+  */
-+  static void add_clipboard_notify(Fl_Clipboard_Notify_Handler h, void *data);
-+  /**
-+  Stop calling the specified callback when there are changes to the selection
-+  buffer or the clipboard.
-+  */
-+  static void remove_clipboard_notify(Fl_Clipboard_Notify_Handler h);
-+  /**
-     Initiate a Drag And Drop operation. The selection buffer should be
-     filled with relevant data before calling this method. FLTK will
-     then initiate the system wide drag and drop handling. Dropped data
-diff -up fltk-1.3.x-r8659/src/Fl.cxx.orig fltk-1.3.x-r8659/src/Fl.cxx
---- fltk-1.3.x-r8659/src/Fl.cxx.orig	2011-05-18 15:20:26.667291459 +0200
-+++ fltk-1.3.x-r8659/src/Fl.cxx	2011-05-18 16:31:15.522026086 +0200
-@@ -430,6 +430,69 @@ static char in_idle;
- #endif
- 
- ////////////////////////////////////////////////////////////////
-+// Clipboard notifications
-+
-+struct Clipboard_Notify {
-+  Fl_Clipboard_Notify_Handler handler;
-+  void *data;
-+  struct Clipboard_Notify *next;
-+};
-+
-+static struct Clipboard_Notify *clip_notify_list = NULL;
-+
-+extern void fl_clipboard_notify_change(); // in Fl_<platform>.cxx
-+
-+void Fl::add_clipboard_notify(Fl_Clipboard_Notify_Handler h, void *data) {
-+  struct Clipboard_Notify *node;
-+
-+  remove_clipboard_notify(h);
-+
-+  node = new Clipboard_Notify;
-+
-+  node->handler = h;
-+  node->data = data;
-+  node->next = clip_notify_list;
-+
-+  clip_notify_list = node;
-+
-+  fl_clipboard_notify_change();
-+}
-+
-+void Fl::remove_clipboard_notify(Fl_Clipboard_Notify_Handler h) {
-+  struct Clipboard_Notify *node, **prev;
-+
-+  node = clip_notify_list;
-+  prev = &clip_notify_list;
-+  while (node != NULL) {
-+    if (node->handler == h) {
-+      *prev = node->next;
-+      delete node;
-+
-+      fl_clipboard_notify_change();
-+
-+      return;
-+    }
-+
-+    prev = &node->next;
-+    node = node->next;
-+  }
-+}
-+
-+bool fl_clipboard_notify_empty(void) {
-+  return clip_notify_list == NULL;
-+}
-+
-+void fl_trigger_clipboard_notify(int source) {
-+  struct Clipboard_Notify *node;
-+
-+  node = clip_notify_list;
-+  while (node != NULL) {
-+    node->handler(source, node->data);
-+    node = node->next;
-+  }
-+}
-+
-+////////////////////////////////////////////////////////////////
- // wait/run/check/ready:
- 
- void (*Fl::idle)(); // see Fl::add_idle.cxx for the add/remove functions
-diff -up fltk-1.3.x-r8659/src/Fl_x.cxx.orig fltk-1.3.x-r8659/src/Fl_x.cxx
---- fltk-1.3.x-r8659/src/Fl_x.cxx.orig	2011-05-17 16:37:11.092011814 +0200
-+++ fltk-1.3.x-r8659/src/Fl_x.cxx	2011-05-18 13:51:06.135475325 +0200
-@@ -309,6 +309,9 @@ static Atom WM_PROTOCOLS;
- static Atom fl_MOTIF_WM_HINTS;
- static Atom TARGETS;
- static Atom CLIPBOARD;
-+static Atom TIMESTAMP;
-+static Atom PRIMARY_TIMESTAMP;
-+static Atom CLIPBOARD_TIMESTAMP;
- Atom fl_XdndAware;
- Atom fl_XdndSelection;
- Atom fl_XdndEnter;
-@@ -678,6 +681,9 @@ void fl_open_display(Display* d) {
-   fl_MOTIF_WM_HINTS     = XInternAtom(d, "_MOTIF_WM_HINTS",     0);
-   TARGETS               = XInternAtom(d, "TARGETS",             0);
-   CLIPBOARD             = XInternAtom(d, "CLIPBOARD",           0);
-+  TIMESTAMP             = XInternAtom(d, "TIMESTAMP",           0);
-+  PRIMARY_TIMESTAMP     = XInternAtom(d, "PRIMARY_TIMESTAMP",   0);
-+  CLIPBOARD_TIMESTAMP   = XInternAtom(d, "CLIPBOARD_TIMESTAMP", 0);
-   fl_XdndAware          = XInternAtom(d, "XdndAware",           0);
-   fl_XdndSelection      = XInternAtom(d, "XdndSelection",       0);
-   fl_XdndEnter          = XInternAtom(d, "XdndEnter",           0);
-@@ -861,6 +881,86 @@ void Fl::copy(const char *stuff, int len
- }
- 
- ////////////////////////////////////////////////////////////////
-+// Code for tracking clipboard changes:
-+
-+static Time primary_timestamp = -1;
-+static Time clipboard_timestamp = -1;
-+
-+extern bool fl_clipboard_notify_empty(void);
-+extern void fl_trigger_clipboard_notify(int source);
-+
-+static void poll_clipboard_owner(void) {
-+  Window xid;
-+
-+  // No one is interested, so no point polling
-+  if (fl_clipboard_notify_empty())
-+    return;
-+
-+  // We need a window for this to work
-+  if (!Fl::first_window())
-+    return;
-+  xid = fl_xid(Fl::first_window());
-+  if (!xid)
-+    return;
-+
-+  // Request an update of the selection time for both the primary and
-+  // clipboard selections. Magic continues when we get a SelectionNotify.
-+  if (!fl_i_own_selection[0])
-+    XConvertSelection(fl_display, XA_PRIMARY, TIMESTAMP, PRIMARY_TIMESTAMP,
-+                      xid, fl_event_time);
-+  if (!fl_i_own_selection[1])
-+    XConvertSelection(fl_display, CLIPBOARD, TIMESTAMP, CLIPBOARD_TIMESTAMP,
-+                      xid, fl_event_time);
-+}
-+
-+static void clipboard_timeout(void *data)
-+{
-+  // No one is interested, so stop polling
-+  if (fl_clipboard_notify_empty())
-+    return;
-+
-+  poll_clipboard_owner();
-+
-+  Fl::repeat_timeout(0.5, clipboard_timeout);
-+}
-+
-+static void handle_clipboard_timestamp(int clipboard, Time time)
-+{
-+  Time *timestamp;
-+
-+  timestamp = clipboard ? &clipboard_timestamp : &primary_timestamp;
-+
-+  // Initial scan, just store the value
-+  if (*timestamp == (Time)-1) {
-+    *timestamp = time;
-+    return;
-+  }
-+
-+  // Same selection
-+  if (time == *timestamp)
-+    return;
-+
-+  *timestamp = time;
-+
-+  // Something happened! Let's tell someone!
-+  fl_trigger_clipboard_notify(clipboard);
-+}
-+
-+void fl_clipboard_notify_change() {
-+  // Reset the timestamps if we've going idle so that you don't
-+  // get a bogus immediate trigger next time they're activated.
-+  if (fl_clipboard_notify_empty()) {
-+    primary_timestamp = -1;
-+    clipboard_timestamp = -1;
-+  } else {
-+    poll_clipboard_owner();
-+
-+    if (!Fl::has_timeout(clipboard_timeout))
-+      Fl::add_timeout(0.5, clipboard_timeout);
-+  }
-+}
-+
-+////////////////////////////////////////////////////////////////
- 
- const XEvent* fl_xevent; // the current x event
- ulong fl_event_time; // the last timestamp from an x event
-@@ -976,7 +1102,6 @@ int fl_handle(const XEvent& thisevent)
-     return 0;
- 
-   case SelectionNotify: {
--    if (!fl_selection_requestor) return 0;
-     static unsigned char* buffer = 0;
-     if (buffer) {XFree(buffer); buffer = 0;}
-     long bytesread = 0;
-@@ -992,6 +1117,19 @@ int fl_handle(const XEvent& thisevent)
-                              bytesread/4, 65536, 1, 0,
-                              &actual, &format, &count, &remaining,
-                              &portion)) break; // quit on error
-+
-+      if ((fl_xevent->xselection.property == PRIMARY_TIMESTAMP) ||
-+          (fl_xevent->xselection.property == CLIPBOARD_TIMESTAMP)) {
-+        if (portion && format == 32 && count == 1) {
-+          Time t = *(unsigned int*)portion;
-+          if (fl_xevent->xselection.property == CLIPBOARD_TIMESTAMP)
-+            handle_clipboard_timestamp(1, t);
-+          else
-+            handle_clipboard_timestamp(0, t);
-+        }
-+        return true;
-+      }
-+
-       if (actual == TARGETS || actual == XA_ATOM) {
- 	Atom type = XA_STRING;
- 	for (unsigned i = 0; i<count; i++) {
-@@ -1029,6 +1167,9 @@ int fl_handle(const XEvent& thisevent)
-       buffer[bytesread] = 0;
-       convert_crlf(buffer, bytesread);
-     }
-+
-+    if (!fl_selection_requestor) return 0;
-+
-     Fl::e_text = buffer ? (char*)buffer : (char *)"";
-     Fl::e_length = bytesread;
-     int old_event = Fl::e_number;
-@@ -1049,6 +1190,7 @@ int fl_handle(const XEvent& thisevent)
-   case SelectionClear: {
-     int clipboard = fl_xevent->xselectionclear.selection == CLIPBOARD;
-     fl_i_own_selection[clipboard] = 0;
-+    poll_clipboard_owner();
-     return 1;}
- 
-   case SelectionRequest: {
-@@ -1248,6 +1390,9 @@ int fl_handle(const XEvent& thisevent)
-   case FocusIn:
-     if (fl_xim_ic) XSetICFocus(fl_xim_ic);
-     event = FL_FOCUS;
-+    // If the user has toggled from another application to this one,
-+    // then it's a good time to check for clipboard changes.
-+    poll_clipboard_owner();
-     break;
- 
-   case FocusOut:
-diff -up fltk-1.3.x-r8659/configh.in.clp-xfixes fltk-1.3.x-r8659/configh.in
---- fltk-1.3.x-r8659/configh.in.clp-xfixes	2011-03-06 17:54:58.000000000 +0100
-+++ fltk-1.3.x-r8659/configh.in	2011-05-19 16:55:27.986364764 +0200
-@@ -117,6 +117,14 @@
- #define USE_XDBE HAVE_XDBE
- 
- /*
-+ * HAVE_XFIXES:
-+ *
-+ * Do we have the X fixes extension?
-+ */
-+
-+#define HAVE_XFIXES 0
-+
-+/*
-  * __APPLE_QUARTZ__:
-  *
-  * All Apple implementations are now based on Quartz and Cocoa,
-diff -up fltk-1.3.x-r8659/configure.in.clp-xfixes fltk-1.3.x-r8659/configure.in
---- fltk-1.3.x-r8659/configure.in.clp-xfixes	2011-05-19 16:55:27.976363265 +0200
-+++ fltk-1.3.x-r8659/configure.in	2011-05-19 16:55:27.987364914 +0200
-@@ -1008,6 +1008,16 @@ case $uname_GUI in
- 		LIBS="-lXext $LIBS")
- 	fi
- 
-+	dnl Check for the Xfixes extension unless disabled...
-+        AC_ARG_ENABLE(xfixes, [  --enable-xfixes       turn on Xfixes support [default=yes]])
-+
-+	if test x$enable_xfixes != xno; then
-+	    AC_CHECK_HEADER(X11/extensions/Xfixes.h, AC_DEFINE(HAVE_XFIXES),,
-+	        [#include <X11/Xlib.h>])
-+	    AC_CHECK_LIB(Xfixes, XFixesQueryExtension,
-+		LIBS="-lXfixes $LIBS")
-+	fi
-+
- 	dnl Check for overlay visuals...
- 	AC_PATH_PROG(XPROP, xprop)
- 	AC_CACHE_CHECK(for X overlay visuals, ac_cv_have_overlay,
-diff -up fltk-1.3.x-r8659/src/Fl_x.cxx.clp-xfixes fltk-1.3.x-r8659/src/Fl_x.cxx
---- fltk-1.3.x-r8659/src/Fl_x.cxx.clp-xfixes	2011-05-19 16:55:27.984364466 +0200
-+++ fltk-1.3.x-r8659/src/Fl_x.cxx	2011-05-19 16:58:06.156112039 +0200
-@@ -53,6 +53,10 @@
- #  include <X11/Xlib.h>
- #  include <X11/keysym.h>
- 
-+#  ifdef HAVE_XFIXES
-+#  include <X11/extensions/Xfixes.h>
-+#  endif
-+
- static Fl_Xlib_Graphics_Driver fl_xlib_driver;
- static Fl_Display_Device fl_xlib_display(&fl_xlib_driver);
- FL_EXPORT Fl_Graphics_Driver *fl_graphics_driver = (Fl_Graphics_Driver*)&fl_xlib_driver; // the current target device of graphics operations
-@@ -303,6 +307,8 @@ XIC fl_xim_ic = 0;
- Window fl_xim_win = 0;
- char fl_is_over_the_spot = 0;
- static XRectangle status_area;
-+static bool have_xfixes = false;
-+static int xfixes_event_base = 0;
- 
- static Atom WM_DELETE_WINDOW;
- static Atom WM_PROTOCOLS;
-@@ -726,6 +732,14 @@ void fl_open_display(Display* d) {
- #if !USE_COLORMAP
-   Fl::visual(FL_RGB);
- #endif
-+
-+#ifdef HAVE_XFIXES
-+  int error_base;
-+  if (XFixesQueryExtension(d, &xfixes_event_base, &error_base))
-+    have_xfixes = true;
-+  else
-+    have_xfixes = false;
-+#endif
- }
- 
- void fl_close_display() {
-@@ -878,6 +892,10 @@ extern void fl_trigger_clipboard_notify(
- static void poll_clipboard_owner(void) {
-   Window xid;
- 
-+  // No polling needed with Xfixes
-+  if (have_xfixes)
-+    return;
-+
-   // No one is interested, so no point polling
-   if (fl_clipboard_notify_empty())
-     return;
-@@ -916,10 +934,12 @@ static void handle_clipboard_timestamp(i
- 
-   timestamp = clipboard ? &clipboard_timestamp : &primary_timestamp;
- 
--  // Initial scan, just store the value
--  if (*timestamp == (Time)-1) {
--    *timestamp = time;
--    return;
-+  if (!have_xfixes) {
-+    // Initial scan, just store the value
-+    if (*timestamp == (Time)-1) {
-+      *timestamp = time;
-+      return;
-+    }
-   }
- 
-   // Same selection
-@@ -939,10 +959,12 @@ void fl_clipboard_notify_change() {
-     primary_timestamp = -1;
-     clipboard_timestamp = -1;
-   } else {
--    poll_clipboard_owner();
-+    if (!have_xfixes) {
-+      poll_clipboard_owner();
- 
--    if (!Fl::has_timeout(clipboard_timeout))
--      Fl::add_timeout(0.5, clipboard_timeout);
-+      if (!Fl::has_timeout(clipboard_timeout))
-+        Fl::add_timeout(0.5, clipboard_timeout);
-+    }
-   }
- }
- 
-@@ -1638,6 +1660,25 @@ int fl_handle(const XEvent& thisevent)
-     }
-   }
- 
-+#ifdef HAVE_XFIXES
-+  switch (xevent.type - xfixes_event_base) {
-+  case XFixesSelectionNotify: {
-+    // Someone feeding us bogus events?
-+    if (!have_xfixes)
-+      return true;
-+
-+    XFixesSelectionNotifyEvent *selection_notify = (XFixesSelectionNotifyEvent *)&xevent;
-+
-+    if ((selection_notify->selection == XA_PRIMARY) && !fl_i_own_selection[0])
-+      handle_clipboard_timestamp(0, selection_notify->selection_timestamp);
-+    else if ((selection_notify->selection == CLIPBOARD) && !fl_i_own_selection[1])
-+      handle_clipboard_timestamp(1, selection_notify->selection_timestamp);
-+
-+    return true;
-+    }
-+  }
-+#endif
-+
-   return Fl::handle(event, window);
- }
- 
-@@ -1871,6 +1912,16 @@ void Fl_X::make_xid(Fl_Window* win, XVis
-     XChangeProperty(fl_display, xp->xid, net_wm_type, XA_ATOM, 32, PropModeReplace, (unsigned char*)&net_wm_type_kind, 1);
-   }
- 
-+#ifdef HAVE_XFIXES
-+  // register for clipboard change notifications
-+  if (have_xfixes && !win->parent()) {
-+    XFixesSelectSelectionInput(fl_display, xp->xid, XA_PRIMARY,
-+                               XFixesSetSelectionOwnerNotifyMask);
-+    XFixesSelectSelectionInput(fl_display, xp->xid, CLIPBOARD,
-+                               XFixesSetSelectionOwnerNotifyMask);
-+  }
-+#endif
-+
-   XMapWindow(fl_display, xp->xid);
-   if (showit) {
-     win->set_visible();
-diff -up fltk-1.3.x-r8659/src/Fl.cxx.orig fltk-1.3.x-r8659/src/Fl.cxx
---- fltk-1.3.x-r8659/src/Fl.cxx.orig	2011-05-18 17:39:15.639513675 +0200
-+++ fltk-1.3.x-r8659/src/Fl.cxx	2011-05-19 13:47:56.082954290 +0200
-@@ -1412,7 +1412,9 @@ int Fl::handle_(int e, Fl_Window* window
- ////////////////////////////////////////////////////////////////
- // hide() destroys the X window, it does not do unmap!
- 
--#if !defined(WIN32) && USE_XFT
-+#if defined(WIN32)
-+extern void fl_update_clipboard(void);
-+#elif USE_XFT
- extern void fl_destroy_xft_draw(Window);
- #endif
- 
-@@ -1459,14 +1461,8 @@ void Fl_Window::hide() {
- #if defined(WIN32)
-   // this little trick keeps the current clipboard alive, even if we are about
-   // to destroy the window that owns the selection.
--  if (GetClipboardOwner()==ip->xid) {
--    Fl_Window *w1 = Fl::first_window();
--    if (w1 && OpenClipboard(fl_xid(w1))) {
--      EmptyClipboard();
--      SetClipboardData(CF_TEXT, NULL);
--      CloseClipboard();
--    }
--  }
-+  if (GetClipboardOwner()==ip->xid)
-+    fl_update_clipboard();
-   // Send a message to myself so that I'll get out of the event loop...
-   PostMessage(ip->xid, WM_APP, 0, 0);
-   if (ip->private_dc) fl_release_dc(ip->xid, ip->private_dc);
-diff -up fltk-1.3.x-r8659/src/Fl_win32.cxx.orig fltk-1.3.x-r8659/src/Fl_win32.cxx
---- fltk-1.3.x-r8659/src/Fl_win32.cxx.orig	2011-05-19 13:48:59.655499725 +0200
-+++ fltk-1.3.x-r8659/src/Fl_win32.cxx	2011-05-19 13:49:31.147228227 +0200
-@@ -552,6 +552,36 @@ public:
-   const char* GetValue() const { return(out); }
- };
- 
-+void fl_update_clipboard(void) {
-+  HWND hwnd = fl_xid(Fl::first_window());
-+
-+  if (!hwnd)
-+    return;
-+
-+  if (!OpenClipboard(hwnd))
-+    return;
-+
-+  EmptyClipboard();
-+
-+  int utf16_len = fl_utf8toUtf16(fl_selection_buffer[1],
-+                                 fl_selection_length[1], 0, 0);
-+
-+  HGLOBAL hMem = GlobalAlloc(GHND, utf16_len * 2 + 2); // moveable and zero'ed mem alloc.
-+  LPVOID memLock = GlobalLock(hMem);
-+
-+  fl_utf8toUtf16(fl_selection_buffer[1], fl_selection_length[1],
-+                 (unsigned short*) memLock, utf16_len + 1);
-+
-+  GlobalUnlock(hMem);
-+  SetClipboardData(CF_UNICODETEXT, hMem);
-+
-+  CloseClipboard();
-+
-+  // In case Windows managed to lob of a WM_DESTROYCLIPBOARD during
-+  // the above.
-+  fl_i_own_selection[1] = 1;
-+}
-+
- // call this when you create a selection:
- void Fl::copy(const char *stuff, int len, int clipboard) {
-   if (!stuff || len<0) return;
-@@ -569,25 +599,9 @@ void Fl::copy(const char *stuff, int len
-   memcpy(fl_selection_buffer[clipboard], stuff, len);
-   fl_selection_buffer[clipboard][len] = 0; // needed for direct paste
-   fl_selection_length[clipboard] = len;
--  if (clipboard) {
--    // set up for "delayed rendering":
--    if (OpenClipboard(NULL)) {
--      // if the system clipboard works, use it
--      int utf16_len = fl_utf8toUtf16(fl_selection_buffer[clipboard], fl_selection_length[clipboard], 0, 0);
--      EmptyClipboard();
--      HGLOBAL hMem = GlobalAlloc(GHND, utf16_len * 2 + 2); // moveable and zero'ed mem alloc.
--      LPVOID memLock = GlobalLock(hMem);
--      fl_utf8toUtf16(fl_selection_buffer[clipboard], fl_selection_length[clipboard], (unsigned short*) memLock, utf16_len + 1);
--      GlobalUnlock(hMem);
--      SetClipboardData(CF_UNICODETEXT, hMem);
--      CloseClipboard();
--      GlobalFree(hMem);
--      fl_i_own_selection[clipboard] = 0;
--    } else {
--      // only if it fails, instruct paste() to use the internal buffers
--      fl_i_own_selection[clipboard] = 1;
--    }
--  }
-+  fl_i_own_selection[clipboard] = 1;
-+  if (clipboard)
-+    fl_update_clipboard();
- }
- 
- // Call this when a "paste" operation happens:
-@@ -1282,34 +1296,6 @@ static LRESULT CALLBACK WndProc(HWND hWn
-     fl_i_own_selection[1] = 0;
-     return 1;
- 
--  case WM_RENDERALLFORMATS:
--    fl_i_own_selection[1] = 0;
--    // Windoze seems unhappy unless I do these two steps. Documentation
--    // seems to vary on whether opening the clipboard is necessary or
--    // is in fact wrong:
--    CloseClipboard();
--    OpenClipboard(NULL);
--    // fall through...
--  case WM_RENDERFORMAT: {
--    HANDLE h;
--
--//  int l = fl_utf_nb_char((unsigned char*)fl_selection_buffer[1], fl_selection_length[1]);
--    int l = fl_utf8toUtf16(fl_selection_buffer[1], fl_selection_length[1], NULL, 0); // Pass NULL buffer to query length required
--    h = GlobalAlloc(GHND, (l+1) * sizeof(unsigned short));
--    if (h) {
--      unsigned short *g = (unsigned short*) GlobalLock(h);
--//    fl_utf2unicode((unsigned char *)fl_selection_buffer[1], fl_selection_length[1], (xchar*)g);
--      l = fl_utf8toUtf16(fl_selection_buffer[1], fl_selection_length[1], g, (l+1));
--      g[l] = 0;
--      GlobalUnlock(h);
--      SetClipboardData(CF_UNICODETEXT, h);
--    }
--
--    // Windoze also seems unhappy if I don't do this. Documentation very
--    // unclear on what is correct:
--    if (fl_msg.message == WM_RENDERALLFORMATS) CloseClipboard();
--    return 1;}
--
-   default:
-     if (Fl::handle(0,0)) return 0;
-     break;
-diff -up fltk-1.3.x-r8659/src/Fl.cxx.win32-fix fltk-1.3.x-r8659/src/Fl.cxx
---- fltk-1.3.x-r8659/src/Fl.cxx.win32-fix	2011-05-19 13:47:56.082954290 +0200
-+++ fltk-1.3.x-r8659/src/Fl.cxx	2011-05-19 13:47:35.540869893 +0200
-@@ -1413,6 +1413,7 @@ int Fl::handle_(int e, Fl_Window* window
- // hide() destroys the X window, it does not do unmap!
- 
- #if defined(WIN32)
-+extern void fl_clipboard_notify_untarget(HWND wnd);
- extern void fl_update_clipboard(void);
- #elif USE_XFT
- extern void fl_destroy_xft_draw(Window);
-@@ -1463,6 +1464,8 @@ void Fl_Window::hide() {
-   // to destroy the window that owns the selection.
-   if (GetClipboardOwner()==ip->xid)
-     fl_update_clipboard();
-+  // Make sure we unlink this window from the clipboard chain
-+  fl_clipboard_notify_untarget(ip->xid);
-   // Send a message to myself so that I'll get out of the event loop...
-   PostMessage(ip->xid, WM_APP, 0, 0);
-   if (ip->private_dc) fl_release_dc(ip->xid, ip->private_dc);
-diff -up fltk-1.3.x-r8659/src/Fl_win32.cxx.win32-fix fltk-1.3.x-r8659/src/Fl_win32.cxx
---- fltk-1.3.x-r8659/src/Fl_win32.cxx.win32-fix	2011-05-19 13:49:31.147228227 +0200
-+++ fltk-1.3.x-r8659/src/Fl_win32.cxx	2011-05-19 13:47:42.548922155 +0200
-@@ -654,6 +654,38 @@ void Fl::paste(Fl_Widget &receiver, int 
-   }
- }
- 
-+static HWND clipboard_wnd = 0;
-+static HWND next_clipboard_wnd = 0;
-+
-+static bool initial_clipboard = true;
-+
-+void fl_clipboard_notify_change() {
-+  // No need to do anything here...
-+}
-+
-+void fl_clipboard_notify_target(HWND wnd) {
-+  if (clipboard_wnd)
-+    return;
-+
-+  // We get one fake WM_DRAWCLIPBOARD immediately, which we therefore
-+  // need to ignore.
-+  initial_clipboard = true;
-+
-+  clipboard_wnd = wnd;
-+  next_clipboard_wnd = SetClipboardViewer(wnd);
-+}
-+
-+void fl_clipboard_notify_untarget(HWND wnd) {
-+  if (wnd != clipboard_wnd)
-+    return;
-+
-+  ChangeClipboardChain(wnd, next_clipboard_wnd);
-+  clipboard_wnd = next_clipboard_wnd = 0;
-+
-+  if (Fl::first_window())
-+    fl_clipboard_notify_target(fl_xid(Fl::first_window()));
-+}
-+
- ////////////////////////////////////////////////////////////////
- char fl_is_ime = 0;
- void fl_get_codepage()
-@@ -1296,6 +1328,27 @@ static LRESULT CALLBACK WndProc(HWND hWn
-     fl_i_own_selection[1] = 0;
-     return 1;
- 
-+  case WM_CHANGECBCHAIN:
-+    if ((hWnd == clipboard_wnd) &&
-+        (next_clipboard_wnd == (HWND)wParam)) {
-+      next_clipboard_wnd = (HWND)lParam;
-+      return 0;
-+    }
-+    break;
-+
-+  case WM_DRAWCLIPBOARD:
-+    // When the clipboard moves between two FLTK windows,
-+    // fl_i_own_selection will temporarily be false as we are
-+    // processing this message. Hence the need to use fl_find().
-+    if (!initial_clipboard && !fl_find(GetClipboardOwner()))
-+      fl_trigger_clipboard_notify(1);
-+    initial_clipboard = false;
-+
-+    if (next_clipboard_wnd)
-+      SendMessage(next_clipboard_wnd, WM_DRAWCLIPBOARD, wParam, lParam);
-+
-+    return 0;
-+
-   default:
-     if (Fl::handle(0,0)) return 0;
-     break;
-@@ -1652,6 +1705,8 @@ Fl_X* Fl_X::make(Fl_Window* w) {
-   x->next = Fl_X::first;
-   Fl_X::first = x;
- 
-+  fl_clipboard_notify_target(x->xid);
-+
-   x->wait_for_expose = 1;
-   if (fl_show_iconic) {showit = 0; fl_show_iconic = 0;}
-   if (showit) {
-diff -up fltk-1.3.x-r8659/src/Fl_cocoa.mm.orig fltk-1.3.x-r8659/src/Fl_cocoa.mm
---- fltk-1.3.x-r8659/src/Fl_cocoa.mm.orig	2011-05-19 14:22:48.558149919 +0200
-+++ fltk-1.3.x-r8659/src/Fl_cocoa.mm	2011-05-19 14:23:49.938366416 +0200
-@@ -1282,9 +1282,13 @@ extern "C" {
- }
- @end
- 
-+static void clipboard_check(void);
-+
- @implementation FLApplication
- + (void)sendEvent:(NSEvent *)theEvent
- {
-+  // update clipboard status
-+  clipboard_check();
-   NSEventType type = [theEvent type];  
-   if (type == NSLeftMouseDown) {
-     fl_lock_function();
-@@ -2647,6 +2651,27 @@ void Fl::paste(Fl_Widget &receiver, int 
-   receiver.handle(FL_PASTE);
- }
- 
-+extern void fl_trigger_clipboard_notify(int source);
-+
-+void fl_clipboard_notify_change() {
-+  // No need to do anything here...
-+}
-+
-+static void clipboard_check(void)
-+{
-+  PasteboardSyncFlags flags;
-+
-+  allocatePasteboard();
-+  flags = PasteboardSynchronize(myPasteboard);
-+
-+  if (!(flags & kPasteboardModified))
-+    return;
-+  if (flags & kPasteboardClientIsOwner)
-+    return;
-+
-+  fl_trigger_clipboard_notify(1);
-+}
-+
- void Fl::add_timeout(double time, Fl_Timeout_Handler cb, void* data)
- {
-   // check, if this timer slot exists already
-diff -bur fltk-1.3.x-r8732.org/documentation/src/enumerations.dox fltk-1.3.x-r8732/documentation/src/enumerations.dox
---- fltk-1.3.x-r8732.org/documentation/src/enumerations.dox	2011-05-11 17:49:30.000000000 +0200
-+++ fltk-1.3.x-r8732/documentation/src/enumerations.dox	2011-05-26 10:15:39.258959203 +0200
-@@ -57,6 +57,7 @@
- \li FL_DND_LEAVE - The mouse pointer left a widget still dragging
-     data. 
- \li FL_DND_RELEASE - Dragged data is about to be dropped. 
-+\li FL_FULLSCREEN - The fullscreen state of the window has changed.
- 
- 
- \section enumerations_when Callback "When" Conditions
-diff -bur fltk-1.3.x-r8732.org/documentation/src/events.dox fltk-1.3.x-r8732/documentation/src/events.dox
---- fltk-1.3.x-r8732.org/documentation/src/events.dox	2011-05-11 17:49:30.000000000 +0200
-+++ fltk-1.3.x-r8732/documentation/src/events.dox	2011-05-26 10:15:39.259959029 +0200
-@@ -300,6 +300,13 @@
- the widget. If the widget returns 1, it will receive the data in
- the immediately following \p FL_PASTE event.
- 
-+\subsection events_fl_fullscreen FL_FULLSCREEN
-+
-+The application window has been changed from normal to fullscreen, or
-+from fullscreen to normal. If you are using a X window manager which
-+supports Extended Window Manager Hints, this event will not be
-+delivered until the change has actually happened. 
-+
- 
- \section events_event_xxx Fl::event_*() methods
- 
-diff -bur fltk-1.3.x-r8732.org/FL/Enumerations.H fltk-1.3.x-r8732/FL/Enumerations.H
---- fltk-1.3.x-r8732.org/FL/Enumerations.H	2011-05-21 23:55:59.000000000 +0200
-+++ fltk-1.3.x-r8732/FL/Enumerations.H	2011-05-26 10:15:39.256959549 +0200
-@@ -292,7 +292,12 @@
-       If the widget returns 1, it will receive the data in the immediately 
-       following FL_PASTE event.
-    */
--  FL_DND_RELEASE	= 23
-+  FL_DND_RELEASE	= 23,
-+
-+  /** The fullscreen state of the window has changed
+  enum Fl_Cursor {
+!   FL_CURSOR_DEFAULT	=  0, /**< the default cursor, usually an arrow. */
+!   FL_CURSOR_ARROW	= 35, /**< an arrow pointer. */
+!   FL_CURSOR_CROSS	= 66, /**< crosshair. */
+!   FL_CURSOR_WAIT	= 76, /**< watch or hourglass. */
+!   FL_CURSOR_INSERT	= 77, /**< I-beam. */
+!   FL_CURSOR_HAND	= 31, /**< hand (uparrow on MSWindows). */
+!   FL_CURSOR_HELP	= 47, /**< question mark. */
+!   FL_CURSOR_MOVE	= 27, /**< 4-pointed arrow. */
+!   // fltk provides bitmaps for these:
+!   FL_CURSOR_NS		= 78, /**< up/down arrow. */
+!   FL_CURSOR_WE		= 79, /**< left/right arrow. */
+!   FL_CURSOR_NWSE	= 80, /**< diagonal arrow. */
+!   FL_CURSOR_NESW	= 81, /**< diagonal arrow. */
+!   FL_CURSOR_NONE	=255, /**< invisible. */
+!   // for back compatibility (non MSWindows ones):
+!   FL_CURSOR_N		= 70, /**< for back compatibility. */
+!   FL_CURSOR_NE		= 69, /**< for back compatibility. */
+!   FL_CURSOR_E		= 49, /**< for back compatibility. */
+!   FL_CURSOR_SE		=  8, /**< for back compatibility. */
+!   FL_CURSOR_S		=  9, /**< for back compatibility. */
+!   FL_CURSOR_SW		=  7, /**< for back compatibility. */
+!   FL_CURSOR_W		= 36, /**< for back compatibility. */
+!   FL_CURSOR_NW		= 68 /**< for back compatibility. */
+  };
+  /*@}*/		// group: Cursors  
+--- 880,913 ----
+  /** The following constants define the mouse cursors that are available in FLTK.
+  
+!     Cursors are provided by the system when available, or bitmaps built into
+!     FLTK as a fallback.
+  
+      \todo enum Fl_Cursor needs maybe an image.
+  */
+  enum Fl_Cursor {
+!   FL_CURSOR_DEFAULT = 0,    /**< the default cursor, usually an arrow. */
+!   FL_CURSOR_ARROW   = 1,    /**< an arrow pointer. */
+!   FL_CURSOR_CROSS   = 2,    /**< crosshair. */
+!   FL_CURSOR_WAIT    = 3,    /**< busy indicator (e.g. hourglass). */
+!   FL_CURSOR_INSERT  = 4,    /**< I-beam. */
+!   FL_CURSOR_HAND    = 5,    /**< pointing hand. */
+!   FL_CURSOR_HELP    = 6,    /**< question mark pointer. */
+!   FL_CURSOR_MOVE    = 7,    /**< 4-pointed arrow or hand. */
+! 
+!   /* Resize indicators */
+!   FL_CURSOR_NS      = 101,  /**< up/down resize. */
+!   FL_CURSOR_WE      = 102,  /**< left/right resize. */
+!   FL_CURSOR_NWSE    = 103,  /**< diagonal resize. */
+!   FL_CURSOR_NESW    = 104,  /**< diagonal resize. */
+!   FL_CURSOR_NE      = 110,  /**< upwards, right resize. */
+!   FL_CURSOR_N       = 111,  /**< upwards resize. */
+!   FL_CURSOR_NW      = 112,  /**< upwards, left resize. */
+!   FL_CURSOR_E       = 113,  /**< leftwards resize. */
+!   FL_CURSOR_W       = 114,  /**< rightwards resize. */
+!   FL_CURSOR_SE      = 115,  /**< downwards, right resize. */
+!   FL_CURSOR_S       = 116,  /**< downwards resize. */
+!   FL_CURSOR_SW      = 117,  /**< downwards, left resize. */
+! 
+!   FL_CURSOR_NONE    = 255,  /**< invisible. */
+  };
+  /*@}*/		// group: Cursors  
+*** fltk-1.3.0/FL/Fl.H	2011-05-23 13:01:29.000000000 -0500
+--- fltk/FL/Fl.H	2011-06-22 22:35:31.000000000 -0500
+***************
+*** 109,112 ****
+--- 109,115 ----
+  typedef int (*Fl_Event_Dispatch)(int event, Fl_Window *w);
+  
++ /** Signature of add_clipboard_notify functions passed as parameters */
++ typedef void (*Fl_Clipboard_Notify_Handler)(int source, void *data);
++ 
+  /** @} */ /* group callback_functions */
+  
+***************
+*** 745,748 ****
+--- 748,764 ----
+    static void paste(Fl_Widget &receiver, int source /*=0*/); // platform dependent
+    /**
++   FLTK will call the registered callback whenever there is a change to the
++   selection buffer or the clipboard. The source argument indicates which
++   of the two has changed. Only changes by other applications are reported.
++   \note Some systems require polling to monitor the clipboard and may
++   therefore have some delay in detecting changes.
 +   */
-+  FL_FULLSCREEN         = 24
-+
- };
- 
- /** \name When Conditions */
-diff -bur fltk-1.3.x-r8732.org/FL/Fl_Widget.H fltk-1.3.x-r8732/FL/Fl_Widget.H
---- fltk-1.3.x-r8732.org/FL/Fl_Widget.H	2011-05-26 10:15:26.146232604 +0200
-+++ fltk-1.3.x-r8732/FL/Fl_Widget.H	2011-05-26 10:15:53.701455256 +0200
-@@ -180,6 +180,7 @@
-         GROUP_RELATIVE  = 1<<16,  ///< position this widget relative to the parent group, not to the window
-         COPIED_TOOLTIP  = 1<<17,  ///< the widget tooltip is internally copied, its destruction is handled by the widget
-         SIMPLE_KEYBOARD = 1<<18,  ///< the widget wants simple, consistent keypresses and not advanced input (like character composition and CJK input)
-+        FULLSCREEN      = 1<<19,  ///< a fullscreen window (Fl_Window)
-         // (space for more flags)
-         USERFLAG3       = 1<<29,  ///< reserved for 3rd party extensions
-         USERFLAG2       = 1<<30,  ///< reserved for 3rd party extensions
-@@ -882,6 +883,9 @@
-   static unsigned int label_shortcut(const char *t);
-   /* Internal use only. */
-   static int test_shortcut(const char*, const bool require_alt = false);
-+  /* Internal use only. */
-+  void _set_fullscreen() {flags_ |= FULLSCREEN;}
-+  void _clear_fullscreen() {flags_ &= ~FULLSCREEN;}
- 
-   /** Checks if w is a child of this widget.
-       \param[in] w potential child widget
-Endast i fltk-1.3.x-r8732/FL: Fl_Widget.H.orig
-diff -bur fltk-1.3.x-r8732.org/FL/Fl_Window.H fltk-1.3.x-r8732/FL/Fl_Window.H
---- fltk-1.3.x-r8732.org/FL/Fl_Window.H	2011-04-15 23:38:05.000000000 +0200
-+++ fltk-1.3.x-r8732/FL/Fl_Window.H	2011-05-26 10:15:39.258959203 +0200
-@@ -69,6 +69,7 @@
-   int minw, minh, maxw, maxh;
-   int dw, dh, aspect;
-   uchar size_range_set;
-+  int no_fullscreen_x, no_fullscreen_y, no_fullscreen_w, no_fullscreen_h;
-   // cursor stuff
-   Fl_Cursor cursor_default;
-   Fl_Color cursor_fg, cursor_bg;
-@@ -384,15 +385,27 @@
-   /**
-     Makes the window completely fill the screen, without any window
-     manager border visible.  You must use fullscreen_off() to undo
--    this. This may not work with all window managers.
-+    this. 
-+
-+    \note On some platforms, this can result in the keyboard being
-+    grabbed. The window may also be recreated, meaning hide() and
-+    show() will be called.
-   */
-   void fullscreen();
-   /**
-+    Turns off any side effects of fullscreen()
++   static void add_clipboard_notify(Fl_Clipboard_Notify_Handler h, void *data);
++   /**
++   Stop calling the specified callback when there are changes to the selection
++   buffer or the clipboard.
++   */
++   static void remove_clipboard_notify(Fl_Clipboard_Notify_Handler h);
++   /**
+      Initiate a Drag And Drop operation. The selection buffer should be
+      filled with relevant data before calling this method. FLTK will
+*** fltk-1.3.0/FL/Fl_Image.H	2011-01-30 03:24:40.000000000 -0600
+--- fltk/FL/Fl_Image.H	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 35,38 ****
+--- 35,39 ----
+  
+  class Fl_Widget;
++ class Fl_Pixmap;
+  struct Fl_Menu_Item;
+  struct Fl_Label;
+***************
+*** 197,200 ****
+--- 198,202 ----
+    Fl_RGB_Image(const uchar *bits, int W, int H, int D=3, int LD=0) :
+      Fl_Image(W,H,D), array(bits), alloc_array(0), id_(0), mask_(0) {data((const char **)&array, 1); ld(LD);}
++   Fl_RGB_Image(const Fl_Pixmap *pxm, Fl_Color bg=FL_GRAY);
+    virtual ~Fl_RGB_Image();
+    virtual Fl_Image *copy(int W, int H);
+*** fltk-1.3.0/FL/Fl_Widget.H	2011-04-24 12:09:41.000000000 -0500
+--- fltk/FL/Fl_Widget.H	2011-06-22 22:41:26.000000000 -0500
+***************
+*** 109,112 ****
+--- 109,113 ----
+  class FL_EXPORT Fl_Widget {
+    friend class Fl_Group;
++   friend class Fl_X;
+  
+    Fl_Group* parent_;
+***************
+*** 180,183 ****
+--- 181,186 ----
+          GROUP_RELATIVE  = 1<<16,  ///< position this widget relative to the parent group, not to the window
+          COPIED_TOOLTIP  = 1<<17,  ///< the widget tooltip is internally copied, its destruction is handled by the widget
++         SIMPLE_KEYBOARD = 1<<18,  ///< the widget wants simple, consistent keypresses and not advanced input (like character composition and CJK input)
++         FULLSCREEN      = 1<<19,  ///< a fullscreen window (Fl_Window)
+          // (space for more flags)
+          USERFLAG3       = 1<<29,  ///< reserved for 3rd party extensions
+***************
+*** 785,788 ****
+--- 788,820 ----
+    void clear_changed() {flags_ &= ~CHANGED;}
+  
++   /** 
++       Returns if the widget sees a simplified keyboard model or not.
++ 
++       Normally widgets get a full-featured keyboard model that is geared
++       towards text input. This includes support for compose sequences and
++       advanced input methods, commonly used for asian writing system. This
++       system however has downsides in that extra graphic can be presented
++       to the user and that a physical key press doesn't correspond directly
++       to a FLTK event.
++ 
++       Widgets that need a direct correspondence between actual key events
++       and those seen by the widget can swith to the simplified keyboard
++       model.
++ 
++      \retval 0 if the widget uses the normal keyboard model
++      \see set_changed(), clear_changed()
++    */
++   unsigned int simple_keyboard() const {return flags_&SIMPLE_KEYBOARD;}
++ 
++   /** Marks a widget to use the simple keyboard model.
++       \see changed(), clear_changed()
++    */
++   void set_simple_keyboard() {flags_ |= SIMPLE_KEYBOARD;}
++ 
++   /** Marks a widget to use the normal keyboard model.
++       \see changed(), set_changed()
++    */
++   void set_normal_keyboard() {flags_ &= ~SIMPLE_KEYBOARD;}
++ 
+    /** Gives the widget the keyboard focus.
+        Tries to make this widget be the Fl::focus() widget, by first sending 
+***************
+*** 853,856 ****
+--- 885,891 ----
+    /* Internal use only. */
+    static int test_shortcut(const char*, const bool require_alt = false);
++   /* Internal use only. */
++   void _set_fullscreen() {flags_ |= FULLSCREEN;}
++   void _clear_fullscreen() {flags_ &= ~FULLSCREEN;}
+  
+    /** Checks if w is a child of this widget.
+*** fltk-1.3.0/FL/Fl_Window.H	2011-04-15 16:38:05.000000000 -0500
+--- fltk/FL/Fl_Window.H	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 38,41 ****
+--- 38,42 ----
+  
+  class Fl_X;
++ class Fl_RGB_Image;
+  
+  /**
+***************
+*** 70,76 ****
+    int dw, dh, aspect;
+    uchar size_range_set;
+    // cursor stuff
+    Fl_Cursor cursor_default;
+-   Fl_Color cursor_fg, cursor_bg;
+    void size_range_();
+    void _Fl_Window(); // constructor innards
+--- 71,77 ----
+    int dw, dh, aspect;
+    uchar size_range_set;
++   int no_fullscreen_x, no_fullscreen_y, no_fullscreen_w, no_fullscreen_h;
+    // cursor stuff
+    Fl_Cursor cursor_default;
+    void size_range_();
+    void _Fl_Window(); // constructor innards
+***************
+*** 385,392 ****
+      Makes the window completely fill the screen, without any window
+      manager border visible.  You must use fullscreen_off() to undo
+!     this. This may not work with all window managers.
+    */
+    void fullscreen();
+    /**
+      Turns off any side effects of fullscreen() and does 
+      resize(x,y,w,h).
+--- 386,401 ----
+      Makes the window completely fill the screen, without any window
+      manager border visible.  You must use fullscreen_off() to undo
+!     this. 
+! 
+!     \note On some platforms, this can result in the keyboard being
+!     grabbed. The window may also be recreated, meaning hide() and
+!     show() will be called.
+    */
+    void fullscreen();
+    /**
++     Turns off any side effects of fullscreen()
++   */
++   void fullscreen_off();
++   /**
+      Turns off any side effects of fullscreen() and does 
+      resize(x,y,w,h).
+***************
+*** 394,397 ****
+--- 403,410 ----
+    void fullscreen_off(int,int,int,int);
+    /**
++     Returns non zero if FULLSCREEN flag is set, 0 otherwise. 
++   */
++   unsigned int fullscreen_active() const { return flags() & FULLSCREEN; }
++   /**
+      Iconifies the window.  If you call this when shown() is false
+      it will show() it as an icon.  If the window is already
+***************
+*** 435,446 ****
+  
+      The type Fl_Cursor is an enumeration defined in <FL/Enumerations.H>.
+-     (Under X you can get any XC_cursor value by passing 
+-     Fl_Cursor((XC_foo/2)+1)).  The colors only work on X, they are
+-     not implemented on WIN32.
+  
+!     For back compatibility only.
+    */
+!   void cursor(Fl_Cursor, Fl_Color=FL_BLACK, Fl_Color=FL_WHITE); // platform dependent
+!   void default_cursor(Fl_Cursor, Fl_Color=FL_BLACK, Fl_Color=FL_WHITE);
+    static void default_callback(Fl_Window*, void* v);
+    
+--- 448,462 ----
+  
+      The type Fl_Cursor is an enumeration defined in <FL/Enumerations.H>.
+  
+!     \see cursor(const Fl_RGB_Image*, int, int), default_cursor()
+    */
+!   void cursor(Fl_Cursor);
+!   void cursor(const Fl_RGB_Image*, int, int);
+!   void default_cursor(Fl_Cursor);
+! 
+!   /* for legacy compatibility */
+!   void cursor(Fl_Cursor c, Fl_Color, Fl_Color=FL_WHITE) { cursor(c); };
+!   void default_cursor(Fl_Cursor c, Fl_Color, Fl_Color=FL_WHITE) { default_cursor(c); };
+! 
+    static void default_callback(Fl_Window*, void* v);
+    
+*** fltk-1.3.0/FL/fl_draw.H	2011-06-02 03:06:09.000000000 -0500
+--- fltk/FL/fl_draw.H	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 758,762 ****
+  FL_EXPORT void fl_overlay_rect(int x,int y,int w,int h);
+  FL_EXPORT void fl_overlay_clear();
+! FL_EXPORT void fl_cursor(Fl_Cursor, Fl_Color fg=FL_BLACK, Fl_Color bg=FL_WHITE);
+  FL_EXPORT const char* fl_expand_text(const char* from, char* buf, int maxbuf,
+                                       double maxw, int& n, double &width,
+--- 758,763 ----
+  FL_EXPORT void fl_overlay_rect(int x,int y,int w,int h);
+  FL_EXPORT void fl_overlay_clear();
+! FL_EXPORT void fl_cursor(Fl_Cursor);
+! FL_EXPORT void fl_cursor(Fl_Cursor, Fl_Color fg, Fl_Color bg=FL_WHITE);
+  FL_EXPORT const char* fl_expand_text(const char* from, char* buf, int maxbuf,
+                                       double maxw, int& n, double &width,
+*** fltk-1.3.0/FL/mac.H	2011-05-12 06:50:43.000000000 -0500
+--- fltk/FL/mac.H	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 142,146 ****
+    WindowRef window_ref(void);
+    void set_key_window(void);
+!   void set_cursor(Fl_Cursor);
+    static CGImageRef CGImage_from_window_rect(Fl_Window *win, int x, int y, int w, int h);
+    static unsigned char *bitmap_from_window_rect(Fl_Window *win, int x, int y, int w, int h, int *bytesPerPixel);
+--- 142,147 ----
+    WindowRef window_ref(void);
+    void set_key_window(void);
+!   int set_cursor(Fl_Cursor);
+!   int set_cursor(const Fl_RGB_Image*, int, int);
+    static CGImageRef CGImage_from_window_rect(Fl_Window *win, int x, int y, int w, int h);
+    static unsigned char *bitmap_from_window_rect(Fl_Window *win, int x, int y, int w, int h, int *bytesPerPixel);
+*** fltk-1.3.0/FL/names.h	2010-11-28 15:06:39.000000000 -0600
+--- fltk/FL/names.h	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 76,79 ****
+--- 76,80 ----
+    "FL_DND_LEAVE",
+    "FL_DND_RELEASE",
++   "FL_FULLSCREEN"
+  };
+  
+*** fltk-1.3.0/FL/win32.H	2011-05-23 13:32:47.000000000 -0500
+--- fltk/FL/win32.H	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 93,96 ****
+--- 93,98 ----
+    void set_minmax(LPMINMAXINFO minmax);
+    void mapraise();
++   int set_cursor(Fl_Cursor);
++   int set_cursor(const Fl_RGB_Image*, int, int);
+    static Fl_X* make(Fl_Window*);
+  };
+*** fltk-1.3.0/FL/x.H	2011-05-21 05:05:19.000000000 -0500
+--- fltk/FL/x.H	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 164,167 ****
+--- 164,169 ----
+    void setwindow(Fl_Window* wi) {w=wi; wi->i=this;}
+    void sendxjunk();
++   int set_cursor(Fl_Cursor);
++   int set_cursor(const Fl_RGB_Image*, int, int);
+    static void make_xid(Fl_Window*,XVisualInfo* =fl_visual, Colormap=fl_colormap);
+    static Fl_X* set_xid(Fl_Window*, Window);
+*** fltk-1.3.0/configh.in	2011-06-09 11:21:40.000000000 -0500
+--- fltk/configh.in	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 118,121 ****
+--- 118,137 ----
+  
+  /*
++  * HAVE_XFIXES:
++  *
++  * Do we have the X fixes extension?
 +  */
-+  void fullscreen_off();
-+  /**
-     Turns off any side effects of fullscreen() and does 
-     resize(x,y,w,h).
-   */
-   void fullscreen_off(int,int,int,int);
-   /**
-+    Returns non zero if FULLSCREEN flag is set, 0 otherwise. 
++ 
++ #define HAVE_XFIXES 0
++ 
++ /*
++  * HAVE_XCURSOR:
++  *
++  * Do we have the X cursor library?
 +  */
-+  unsigned int fullscreen_active() const { return flags() & FULLSCREEN; }
-+  /**
-     Iconifies the window.  If you call this when shown() is false
-     it will show() it as an icon.  If the window is already
-     iconified this does nothing.
-diff -bur fltk-1.3.x-r8732.org/FL/names.h fltk-1.3.x-r8732/FL/names.h
---- fltk-1.3.x-r8732.org/FL/names.h	2010-11-28 22:06:39.000000000 +0100
-+++ fltk-1.3.x-r8732/FL/names.h	2011-05-26 10:15:39.257959376 +0200
-@@ -75,6 +75,7 @@
-   "FL_DND_DRAG",
-   "FL_DND_LEAVE",
-   "FL_DND_RELEASE",
-+  "FL_FULLSCREEN"
- };
- 
- /**
-diff -bur fltk-1.3.x-r8732.org/src/Fl_cocoa.mm fltk-1.3.x-r8732/src/Fl_cocoa.mm
---- fltk-1.3.x-r8732.org/src/Fl_cocoa.mm	2011-05-26 10:15:26.168228790 +0200
-+++ fltk-1.3.x-r8732/src/Fl_cocoa.mm	2011-05-26 10:15:39.255959723 +0200
-@@ -649,6 +649,10 @@
- {
-   containsGLsubwindow = contains;
- }
-+- (BOOL)canBecomeKeyWindow
-+{
-+  return YES;
-+}
- @end
- 
- @interface FLApplication : NSObject
-@@ -1087,6 +1091,10 @@
-   fl_lock_function();
-   FLWindow *nsw = (FLWindow*)[notif object];
-   Fl_Window *window = [nsw getFl_Window];
-+  /* Fullscreen windows obscure all other windows so we need to return
-+     to a "normal" level when the user switches to another window */
-+  if (window->fullscreen_active())
-+    [nsw setLevel:NSNormalWindowLevel];
-   Fl::handle( FL_UNFOCUS, window);
-   fl_unlock_function();
- }
-@@ -1095,6 +1103,9 @@
-   fl_lock_function();
-   FLWindow *nsw = (FLWindow*)[notif object];
-   Fl_Window *w = [nsw getFl_Window];
-+  /* Restore previous fullscreen level */
-+  if (w->fullscreen_active())
-+    [nsw setLevel:NSStatusWindowLevel];
-   if ( w->border() || (!w->modal() && !w->tooltip_window()) ) Fl::handle( FL_FOCUS, w);
-   fl_unlock_function();
- }
-@@ -2087,6 +2098,22 @@
- 
- @end
- 
-+void fullscreen_x(Fl_Window *w) {
-+  w->_set_fullscreen();
-+  /* On OS X < 10.6, it is necessary to recreate the window. This is done
-+     with hide+show. */
-+  w->hide();
-+  w->show();
-+  Fl::handle(FL_FULLSCREEN, w);
-+}
-+
-+void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H) {
-+  w->_clear_fullscreen();
-+  w->hide();
-+  w->resize(X, Y, W, H);
-+  w->show();
-+  Fl::handle(FL_FULLSCREEN, w);
-+}
- 
- /*
-  * go ahead, create that (sub)window
-@@ -2210,6 +2237,13 @@
-     x->gc = 0;
- 	  
-     NSRect srect = [[NSScreen mainScreen] frame];
-+    if (w->flags() & Fl_Widget::FULLSCREEN) {
-+      int sx, sy, sw, sh;
-+      Fl::screen_xywh(sx, sy, sw, sh, w->x(), w->y(), w->w(), w->h());
-+      w->resize(sx, sy, sw, sh);
-+      winstyle = NSBorderlessWindowMask;
-+      winlevel = NSStatusWindowLevel;
-+    }
-     NSRect crect;
-     crect.origin.x = w->x(); 
-     crect.origin.y = srect.size.height - (w->y() + w->h());
-Endast i fltk-1.3.x-r8732/src: Fl_cocoa.mm.orig
-diff -bur fltk-1.3.x-r8732.org/src/Fl_grab.cxx fltk-1.3.x-r8732/src/Fl_grab.cxx
---- fltk-1.3.x-r8732.org/src/Fl_grab.cxx	2011-05-26 10:15:26.147232431 +0200
-+++ fltk-1.3.x-r8732/src/Fl_grab.cxx	2011-05-26 10:15:39.250960589 +0200
-@@ -51,7 +51,19 @@
- extern void *fl_capture;
- #endif
- 
-+#if !(defined(WIN32) || defined(__APPLE__))
-+extern int ewmh_supported(); // from Fl_x.cxx
-+#endif
-+
- void Fl::grab(Fl_Window* win) {
-+    Fl_Window *fullscreen_win = NULL;
-+    for (Fl_Window *W = Fl::first_window(); W; W = Fl::next_window(W)) {
-+      if (W->fullscreen_active()) {
-+        fullscreen_win = W;
-+        break;
-+      }
-+    }
-+
-   if (win) {
-     if (!grab_) {
- #ifdef WIN32
-@@ -61,8 +73,9 @@
-       fl_capture = Fl_X::i(first_window())->xid;
-       Fl_X::i(first_window())->set_key_window();
- #else
-+      Window xid = fullscreen_win ? fl_xid(fullscreen_win) : fl_xid(first_window());
-       XGrabPointer(fl_display,
--		   fl_xid(first_window()),
-+		   xid,
- 		   1,
- 		   ButtonPressMask|ButtonReleaseMask|
- 		   ButtonMotionMask|PointerMotionMask,
-@@ -72,7 +85,7 @@
- 		   0,
- 		   fl_event_time);
-       XGrabKeyboard(fl_display,
--		    fl_xid(first_window()),
-+		    xid,
- 		    1,
- 		    GrabModeAsync,
- 		    GrabModeAsync, 
-@@ -89,7 +102,10 @@
- #elif defined(__APPLE__)
-       fl_capture = 0;
- #else
-+      // We must keep the grab in the non-EWMH fullscreen case
-+      if (!fullscreen_win || ewmh_supported()) {
-       XUngrabKeyboard(fl_display, fl_event_time);
-+      }
-       XUngrabPointer(fl_display, fl_event_time);
-       // this flush is done in case the picked menu item goes into
-       // an infinite loop, so we don't leave the X server locked up:
-Endast i fltk-1.3.x-r8732/src: Fl_grab.cxx.orig
-diff -bur fltk-1.3.x-r8732.org/src/Fl_win32.cxx fltk-1.3.x-r8732/src/Fl_win32.cxx
---- fltk-1.3.x-r8732.org/src/Fl_win32.cxx	2011-05-26 10:15:26.165229310 +0200
-+++ fltk-1.3.x-r8732/src/Fl_win32.cxx	2011-05-26 10:15:39.252960243 +0200
-@@ -1490,6 +1490,11 @@
-   X+=xoff;
-   Y+=yoff;
- 
-+  if (w->flags() & Fl_Widget::FULLSCREEN) {
-+    X = Y = 0;
-+    bx = by = bt = 0;
-+  }
-+
-   return ret;
- }
- 
-@@ -1540,6 +1545,58 @@
-   }
- }
- 
-+static void make_fullscreen(Fl_Window *w, Window xid, int X, int Y, int W, int H) {
-+  int sx, sy, sw, sh;
-+  Fl::screen_xywh(sx, sy, sw, sh, X, Y, W, H);
-+  DWORD flags = GetWindowLong(xid, GWL_STYLE);
-+  flags = flags & ~(WS_THICKFRAME|WS_CAPTION);
-+  SetWindowLong(xid, GWL_STYLE, flags);
-+  // SWP_NOSENDCHANGING is so that we can override size limits
-+  SetWindowPos(xid, HWND_TOP, sx, sy, sw, sh, SWP_NOSENDCHANGING | SWP_FRAMECHANGED);
-+}
-+
-+void fullscreen_x(Fl_Window *w) {
-+  w->_set_fullscreen();
-+  make_fullscreen(w, fl_xid(w), w->x(), w->y(), w->w(), w->h());
-+  Fl::handle(FL_FULLSCREEN, w);
-+}
-+
-+void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H) {
-+  w->_clear_fullscreen();
-+  DWORD style = GetWindowLong(fl_xid(w), GWL_STYLE);
-+  // Remove the xid temporarily so that Fl_X::fake_X_wm() behaves like it
-+  // does in Fl_X::make().
-+  HWND xid = fl_xid(w);
-+  Fl_X::i(w)->xid = NULL;
-+  int x, y, bt, bx, by;
-+  switch (Fl_X::fake_X_wm(w, x, y, bt, bx, by)) {
-+  case 0: 
-+    break;
-+  case 1: 
-+    style |= WS_CAPTION; 
-+    break;
-+  case 2: 
-+    if (w->border()) {
-+      style |= WS_THICKFRAME | WS_CAPTION; 
-+    }
-+    break;
-+  }
-+  Fl_X::i(w)->xid = xid;
-+  // Adjust for decorations (but not if that puts the decorations
-+  // outside the screen)
-+  if ((X != w->x()) || (Y != w->y())) {
-+    X -= bx;
-+    Y -= by+bt;
-+  }
-+  W += bx*2;
-+  H += by*2+bt;
-+  SetWindowLong(fl_xid(w), GWL_STYLE, style);
-+  SetWindowPos(fl_xid(w), 0, X, Y, W, H,
-+               SWP_NOACTIVATE | SWP_NOZORDER | SWP_FRAMECHANGED);
-+  Fl::handle(FL_FULLSCREEN, w);
-+}
-+
-+
- ////////////////////////////////////////////////////////////////
- 
- /*
-@@ -1669,18 +1726,26 @@ Fl_X* Fl_X::make(Fl_Window* w) {
-     int xwm = xp , ywm = yp , bt, bx, by;
-     switch (fake_X_wm(w, xwm, ywm, bt, bx, by)) {
-       // No border (used for menus)
--      case 0: style |= WS_POPUP;
--              styleEx |= WS_EX_TOOLWINDOW;
-+      case 0:
-+        style |= WS_POPUP;
-+        styleEx |= WS_EX_TOOLWINDOW;
- 	      break;
- 
-       // Thin border and title bar
--      case 1: style |= WS_DLGFRAME | WS_CAPTION; break;
-+      case 1:
-+        style |= WS_DLGFRAME | WS_CAPTION;
-+        if (!w->modal())
-+          style |= WS_SYSMENU | WS_MINIMIZEBOX;
-+        break;
- 
-       // Thick, resizable border and title bar, with maximize button
--      case 2: style |= WS_THICKFRAME | WS_MAXIMIZEBOX | WS_CAPTION ; break;
-+      case 2:
-+        style |= WS_THICKFRAME | WS_SYSMENU | WS_MAXIMIZEBOX | WS_CAPTION;
-+        if (!w->modal())
-+          style |= WS_MINIMIZEBOX;
-+        break;
-     }
-     if (by+bt) {
--      if (!w->modal()) style |= WS_SYSMENU | WS_MINIMIZEBOX;
-       wp += 2*bx;
-       hp += 2*by+bt;
-     }
-@@ -1736,6 +1801,18 @@
-   );
-   if (lab) free(lab);
- 
-+  if (w->flags() & Fl_Widget::FULLSCREEN) {
-+  /* We need to make sure that the fullscreen is created on the
-+     default monitor, ie the desktop where the shortcut is located
-+     etc. This requires that CreateWindow is called with CW_USEDEFAULT
-+     for x and y. We can then use GetWindowRect to determine which
-+     monitor the window was placed on. */
-+    RECT rect;
-+    GetWindowRect(x->xid, &rect);
-+    make_fullscreen(w, x->xid, rect.left, rect.top, 
-+                    rect.right - rect.left, rect.bottom - rect.top);
-+  }
-+
-   x->next = Fl_X::first;
-   Fl_X::first = x;
- 
-@@ -1753,7 +1830,7 @@
-   // If we've captured the mouse, we dont want to activate any
-   // other windows from the code, or we lose the capture.
-   ShowWindow(x->xid, !showit ? SW_SHOWMINNOACTIVE :
--	     (Fl::grab() || (style & WS_POPUP)) ? SW_SHOWNOACTIVATE : SW_SHOWNORMAL);
-+	     (Fl::grab() || (styleEx & WS_EX_TOOLWINDOW)) ? SW_SHOWNOACTIVATE : SW_SHOWNORMAL);
- 
-   // Register all windows for potential drag'n'drop operations
-   fl_OleInitialize();
-Endast i fltk-1.3.x-r8732/src: Fl_win32.cxx.orig
-diff -bur fltk-1.3.x-r8732.org/src/Fl_Window.cxx fltk-1.3.x-r8732/src/Fl_Window.cxx
---- fltk-1.3.x-r8732.org/src/Fl_Window.cxx	2011-02-25 09:44:47.000000000 +0100
-+++ fltk-1.3.x-r8732/src/Fl_Window.cxx	2011-05-26 10:15:39.250960589 +0200
-@@ -59,6 +59,10 @@
-   resizable(0);
-   size_range_set = 0;
-   minw = maxw = minh = maxh = 0;
-+  no_fullscreen_x = 0;
-+  no_fullscreen_y = 0;
-+  no_fullscreen_w = w();
-+  no_fullscreen_h = h();
-   callback((Fl_Callback*)default_callback);
- }
- 
-diff -bur fltk-1.3.x-r8732.org/src/Fl_Window_fullscreen.cxx fltk-1.3.x-r8732/src/Fl_Window_fullscreen.cxx
---- fltk-1.3.x-r8732.org/src/Fl_Window_fullscreen.cxx	2011-03-12 22:36:21.000000000 +0100
-+++ fltk-1.3.x-r8732/src/Fl_Window_fullscreen.cxx	2011-05-26 10:15:39.249960763 +0200
-@@ -60,39 +60,48 @@
- #endif
- }
- 
-+void fullscreen_x(Fl_Window *w);
-+void fullscreen_off_x();
-+void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H);
-+
-+/* Note: The previous implementation toggled border(). With this new
-+   implementation this is not necessary. Additionally, if we do that,
-+   the application may lose focus when switching out of fullscreen
-+   mode with some window managers. Besides, the API does not say that
-+   the FLTK border state should be toggled; it only says that the
-+   borders should not be *visible*. 
-+*/
- void Fl_Window::fullscreen() {
--#ifndef WIN32
--  //this would clobber the fake wm, since it relies on the border flags to
--  //determine its thickness
--  border(0);
--#endif
--#if defined(__APPLE__) || defined(WIN32) || defined(USE_X11)
--  int sx, sy, sw, sh;
--  Fl::screen_xywh(sx, sy, sw, sh, x(), y(), w(), h());
--  // if we are on the main screen, we will leave the system menu bar unobstructed
--  if (Fl::x()>=sx && Fl::y()>=sy && Fl::x()+Fl::w()<=sx+sw && Fl::y()+Fl::h()<=sy+sh) {
--    sx = Fl::x(); sy = Fl::y(); 
--    sw = Fl::w(); sh = Fl::h();
-+  if (shown() && !(flags() & Fl_Widget::FULLSCREEN)) {
-+    no_fullscreen_x = x();
-+    no_fullscreen_y = y();
-+    no_fullscreen_w = w();
-+    no_fullscreen_h = h();
-+    fullscreen_x(this);
-+  } else {
-+    set_flag(FULLSCREEN);
-   }
--  if (x()==sx) x(sx+1); // make sure that we actually execute the resize
--#if defined(USE_X11)
--  resize(0, 0, w(), h()); // work around some quirks in X11
--#endif
--  resize(sx, sy, sw, sh);
--#else
--  if (!x()) x(1); // make sure that we actually execute the resize
--  resize(0,0,Fl::w(),Fl::h());
--#endif
- }
- 
- void Fl_Window::fullscreen_off(int X,int Y,int W,int H) {
--  // this order produces less blinking on IRIX:
--  resize(X,Y,W,H);
--#ifndef WIN32
--  border(1);
--#endif
-+  if (shown() && (flags() & Fl_Widget::FULLSCREEN)) {
-+    fullscreen_off_x(this, X, Y, W, H);
-+  } else {
-+    clear_flag(FULLSCREEN);
-+  }
-+  no_fullscreen_x = no_fullscreen_y = no_fullscreen_w = no_fullscreen_h = 0;
- }
- 
-+void Fl_Window::fullscreen_off() {
-+  if (!no_fullscreen_x && !no_fullscreen_y) {
-+    // Window was initially created fullscreen - default to current monitor
-+    no_fullscreen_x = x();
-+    no_fullscreen_y = y();
-+  }
-+  fullscreen_off(no_fullscreen_x, no_fullscreen_y, no_fullscreen_w, no_fullscreen_h);
-+}
-+
-+
- //
- // End of "$Id: Fl_Window_fullscreen.cxx 8515 2011-03-12 21:36:21Z manolo $".
- //
-Endast i fltk-1.3.x-r8732/src: Fl_Window_fullscreen.cxx.orig
-diff -bur fltk-1.3.x-r8732.org/src/Fl_x.cxx fltk-1.3.x-r8732/src/Fl_x.cxx
---- fltk-1.3.x-r8732.org/src/Fl_x.cxx	2011-05-26 10:15:26.159230350 +0200
-+++ fltk-1.3.x-r8732/src/Fl_x.cxx	2011-05-26 10:15:39.253960069 +0200
-@@ -338,6 +338,9 @@
- Atom fl_XaTextUriList;
- Atom fl_NET_WM_NAME;			// utf8 aware window label
- Atom fl_NET_WM_ICON_NAME;		// utf8 aware window icon name
-+Atom fl_NET_SUPPORTING_WM_CHECK;
-+Atom fl_NET_WM_STATE;
-+Atom fl_NET_WM_STATE_FULLSCREEN;
- 
- /*
-   X defines 32-bit-entities to have a format value of max. 32,
-@@ -711,6 +714,9 @@
-   fl_XaTextUriList      = XInternAtom(d, "text/uri-list",       0);
-   fl_NET_WM_NAME        = XInternAtom(d, "_NET_WM_NAME",        0);
-   fl_NET_WM_ICON_NAME   = XInternAtom(d, "_NET_WM_ICON_NAME",   0);
-+  fl_NET_SUPPORTING_WM_CHECK = XInternAtom(d, "_NET_SUPPORTING_WM_CHECK", 0);
-+  fl_NET_WM_STATE       = XInternAtom(d, "_NET_WM_STATE",       0);
-+  fl_NET_WM_STATE_FULLSCREEN = XInternAtom(d, "_NET_WM_STATE_FULLSCREEN", 0);
- 
-   if (sizeof(Atom) < 4)
-     atom_bits = sizeof(Atom) * 8;
-@@ -862,6 +868,31 @@
-   XSendEvent(fl_display, window, 0, 0, &e);
- }
- 
-+
-+/* 
-+   Get window property value (32 bit format) 
-+   Returns zero on success, -1 on error
-+*/
-+static int get_xwinprop(Window wnd, Atom prop, long max_length,
-+                        unsigned long *nitems, unsigned long **data) {
-+  Atom actual;
-+  int format;
-+  unsigned long bytes_after;
-+  
-+  if (Success != XGetWindowProperty(fl_display, wnd, prop, 0, max_length, 
-+                                    False, AnyPropertyType, &actual, &format, 
-+                                    nitems, &bytes_after, (unsigned char**)data)) {
-+    return -1;
-+  }
-+
-+  if (actual == None || format != 32) {
-+    return -1;
-+  }
-+
-+  return 0;
-+}
-+
-+
- ////////////////////////////////////////////////////////////////
- // Code for copying to clipboard and DnD out of the program:
- 
-@@ -1631,6 +1662,31 @@
-     in_a_window = true;
-     break;
- 
-+  case PropertyNotify:
-+    if (xevent.xproperty.atom == fl_NET_WM_STATE) {
-+      int fullscreen_state = 0;
-+      if (xevent.xproperty.state != PropertyDelete) {
-+        unsigned long nitems;
-+        unsigned long *words = 0;
-+        if (0 == get_xwinprop(xid, fl_NET_WM_STATE, 64, &nitems, &words) ) { 
-+          for (unsigned long item = 0; item < nitems; item++) {
-+            if (words[item] == fl_NET_WM_STATE_FULLSCREEN) {
-+              fullscreen_state = 1;
-+            }
-+          }
-+        }
-+      }
-+      if (window->fullscreen_active() && !fullscreen_state) {
-+        window->_clear_fullscreen();
-+        event = FL_FULLSCREEN;
-+      }
-+      if (!window->fullscreen_active() && fullscreen_state) {
-+        window->_set_fullscreen();
-+        event = FL_FULLSCREEN;
-+      }
-+    }
-+    break;
-+
-   case MotionNotify:
-     set_event_xy();
- #  if CONSOLIDATE_MOTION
-@@ -1789,6 +1845,75 @@
- 
- ////////////////////////////////////////////////////////////////
- 
-+#define _NET_WM_STATE_REMOVE        0  /* remove/unset property */
-+#define _NET_WM_STATE_ADD           1  /* add/set property */
-+#define _NET_WM_STATE_TOGGLE        2  /* toggle property  */
-+
-+static void send_wm_state_event(Window wnd, int add, Atom prop) {
-+  XEvent e;
-+  e.xany.type = ClientMessage;
-+  e.xany.window = wnd;
-+  e.xclient.message_type = fl_NET_WM_STATE;
-+  e.xclient.format = 32;
-+  e.xclient.data.l[0] = add ? _NET_WM_STATE_ADD : _NET_WM_STATE_REMOVE;
-+  e.xclient.data.l[1] = prop;
-+  e.xclient.data.l[2] = 0;
-+  e.xclient.data.l[3] = 0;
-+  e.xclient.data.l[4] = 0;
-+  XSendEvent(fl_display, RootWindow(fl_display, fl_screen),
-+             0, SubstructureNotifyMask | SubstructureRedirectMask,
-+             &e);
-+}
-+
-+int ewmh_supported() {
-+  static int result = -1;
-+
-+  if (result == -1) {
-+    result = 0;
-+    unsigned long nitems;
-+    unsigned long *words = 0;
-+    if (0 == get_xwinprop(XRootWindow(fl_display, fl_screen), fl_NET_SUPPORTING_WM_CHECK, 64,
-+                          &nitems, &words) && nitems == 1) {
-+      Window child = words[0];
-+      if (0 == get_xwinprop(child, fl_NET_SUPPORTING_WM_CHECK, 64,
-+                           &nitems, &words) && nitems == 1) {
-+        result = (child == words[0]);
-+      }
-+    }
-+  }
-+
-+  return result;
-+}
-+
-+/* Change an existing window to fullscreen */
-+void fullscreen_x(Fl_Window *w) {
-+  if (ewmh_supported()) {
-+    send_wm_state_event(fl_xid(w), 1, fl_NET_WM_STATE_FULLSCREEN);
-+  } else {
-+    w->_set_fullscreen();
-+    w->hide();
-+    w->show();
-+    /* We want to grab the window, not a widget, so we cannot use Fl::grab */
-+    XGrabKeyboard(fl_display, fl_xid(w), 1, GrabModeAsync, GrabModeAsync, fl_event_time);
-+    Fl::handle(FL_FULLSCREEN, w);
-+  }
-+}
-+
-+void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H) {
-+  if (ewmh_supported()) {
-+    send_wm_state_event(fl_xid(w), 0, fl_NET_WM_STATE_FULLSCREEN);
-+  } else {
-+    w->_clear_fullscreen();
-+    /* The grab will be lost when the window is destroyed */
-+    w->hide();
-+    w->resize(X,Y,W,H);
-+    w->show();
-+    Fl::handle(FL_FULLSCREEN, w);
-+  }
-+}
-+
-+////////////////////////////////////////////////////////////////
-+
- // A subclass of Fl_Window may call this to associate an X window it
- // creates with the Fl_Window:
- 
-@@ -1824,6 +1949,7 @@
- |KeyPressMask|KeyReleaseMask|KeymapStateMask|FocusChangeMask
- |ButtonPressMask|ButtonReleaseMask
- |EnterWindowMask|LeaveWindowMask
-+|PropertyChangeMask
- |PointerMotionMask;
- 
- void Fl_X::make_xid(Fl_Window* win, XVisualInfo *visual, Colormap colormap)
-@@ -1895,6 +2021,16 @@
-     attr.save_under = 1; mask |= CWSaveUnder;
-     if (!win->border()) {attr.override_redirect = 1; mask |= CWOverrideRedirect;}
-   }
-+  // For the non-EWMH fullscreen case, we cannot use the code above,
-+  // since we do not want save_under, do not want to turn off the
-+  // border, and cannot grab without an existing window. Besides, 
-+  // there is no clear_override(). 
-+  if (win->flags() & Fl_Widget::FULLSCREEN && !ewmh_supported()) {
-+    attr.override_redirect = 1;
-+    mask |= CWOverrideRedirect;
-+    Fl::screen_xywh(X, Y, W, H, X, Y, W, H);
-+  }
-+
-   if (fl_background_pixel >= 0) {
-     attr.background_pixel = fl_background_pixel;
-     fl_background_pixel = -1;
-@@ -1954,6 +2090,12 @@
-           PropModeAppend, (unsigned char*) &net_wm_state_skip_taskbar, 1);
-     }
- 
-+    // If asked for, create fullscreen
-+    if (win->flags() & Fl_Widget::FULLSCREEN && ewmh_supported()) {
-+      XChangeProperty (fl_display, xp->xid, fl_NET_WM_STATE, XA_ATOM, 32,
-+                       PropModeAppend, (unsigned char*) &fl_NET_WM_STATE_FULLSCREEN, 1);
-+    }
-+
-     // Make it receptive to DnD:
-     long version = 4;
-     XChangeProperty(fl_display, xp->xid, fl_XdndAware,
-@@ -2001,6 +2143,12 @@
-     Fl::e_number = old_event;
-     win->redraw();
-   }
-+
-+  // non-EWMH fullscreen case, need grab
-+  if (win->flags() & Fl_Widget::FULLSCREEN && !ewmh_supported()) {
-+    XGrabKeyboard(fl_display, xp->xid, 1, GrabModeAsync, GrabModeAsync, fl_event_time);
-+  }
-+
- }
- 
- ////////////////////////////////////////////////////////////////
-Endast i fltk-1.3.x-r8732/src: Fl_x.cxx.orig
-diff -bur fltk-1.3.x-r8732.org/test/fullscreen.cxx fltk-1.3.x-r8732/test/fullscreen.cxx
---- fltk-1.3.x-r8732.org/test/fullscreen.cxx	2010-12-15 13:11:16.000000000 +0100
-+++ fltk-1.3.x-r8732/test/fullscreen.cxx	2011-05-26 10:15:39.258959203 +0200
-@@ -60,8 +60,11 @@
- #include <FL/Fl.H>
- #include <FL/Fl_Single_Window.H>
- #include <FL/Fl_Hor_Slider.H>
-+#include <FL/Fl_Input.H>
-+#include <FL/Fl_Menu_Button.H>
- #include <FL/Fl_Toggle_Light_Button.H>
- #include <FL/math.h>
-+#include <FL/fl_ask.H>
- #include <stdio.h>
- 
- #if HAVE_GL
-@@ -124,6 +127,28 @@
- 
- #endif
- 
-+class fullscreen_window : public Fl_Single_Window {
-+
-+  public:
-+  fullscreen_window(int W, int H, const char *t=0);
-+  int handle (int e);
-+  Fl_Toggle_Light_Button *b3;
-+
-+};
-+
-+fullscreen_window::fullscreen_window(int W, int H, const char *t) : Fl_Single_Window(W, H, t) { 
-+
-+}
-+
-+int fullscreen_window::handle(int e) {
-+  if (e == FL_FULLSCREEN) {
-+    printf("Recieved FL_FULLSCREEN event\n");
-+    b3->value(fullscreen_active());
-+  }
-+  if (Fl_Single_Window::handle(e)) return 1;
-+  return 0;
-+}
-+
- void sides_cb(Fl_Widget *o, void *p) {
-   shape_window *sw = (shape_window *)p;
-   sw->sides = int(((Fl_Slider *)o)->value());
-@@ -161,13 +186,14 @@
-     py = w->y();
-     pw = w->w();
-     ph = w->h();
--#ifndef WIN32//necessary because fullscreen removes border
--	border_button->value(0);
--	border_button->do_callback();
--#endif
-     w->fullscreen();
-+    w->override();
-+#ifndef WIN32 // update our border state in case border was turned off
-+    border_button->value(w->border());
-+#endif
-   } else {
--    w->fullscreen_off(px,py,pw,ph);
-+    //w->fullscreen_off(px,py,pw,ph);
-+    w->fullscreen_off();
-   }
- }
- 
-@@ -177,7 +203,7 @@
-   exit(0);
- }
- 
--#define NUMB 5
-+#define NUMB 6
- 
- int twowindow = 0;
- int initfull = 0;
-@@ -193,7 +219,7 @@
-   if (Fl::args(argc,argv,i,arg) < argc)
-     Fl::fatal("Options are:\n -2 = 2 windows\n -f = startup fullscreen\n%s",Fl::help);
- 
--  Fl_Single_Window window(300,300+30*NUMB); window.end();
-+  fullscreen_window window(300,300+30*NUMB); window.end();
- 
-   shape_window sw(10,10,window.w()-20,window.h()-30*NUMB-20);
- #if HAVE_GL
-@@ -228,21 +254,24 @@
-   b1.callback(double_cb,&sw);
-   y+=30;
- 
-+  Fl_Input i1(50,y,window.w()-60,30, "Input");
-+  y+=30;
-+
-   Fl_Toggle_Light_Button b2(50,y,window.w()-60,30,"Border");
-   b2.callback(border_cb,w);
-   b2.set();
-   border_button = &b2;
-   y+=30;
- 
--  Fl_Toggle_Light_Button b3(50,y,window.w()-60,30,"FullScreen");
--  b3.callback(fullscreen_cb,w);
-+  window.b3 = new Fl_Toggle_Light_Button(50,y,window.w()-60,30,"FullScreen");
-+  window.b3->callback(fullscreen_cb,w);
-   y+=30;
- 
-   Fl_Button eb(50,y,window.w()-60,30,"Exit");
-   eb.callback(exit_cb);
-   y+=30;
- 
--  if (initfull) {b3.set(); b3.do_callback();}
-+  if (initfull) {window.b3->set(); window.b3->do_callback();}
- 
-   window.end();
-   window.show(argc,argv);
-Index: fltk-1.3.x-r8772/src/Fl_Image.cxx
-===================================================================
---- fltk-1.3.x-r8772/src/Fl_Image.cxx	(revision 8771)
-+++ fltk-1.3.x-r8772/src/Fl_Image.cxx	(working copy)
-@@ -172,6 +172,19 @@
- //
- // RGB image class...
- //
-+
-+int fl_convert_pixmap(const char*const* cdata, uchar* out, Fl_Color bg);
-+
-+/** The constructor creates a new RGBA image from the specified Fl_Pixmap. */
-+Fl_RGB_Image::Fl_RGB_Image(const Fl_Pixmap *pxm, Fl_Color bg):
-+  Fl_Image(pxm->w(), pxm->h(), 4), id_(0), mask_(0)
-+{
-+  array = new uchar[w() * h() * d()];
-+  alloc_array = 1;
-+  fl_convert_pixmap(pxm->data(), (uchar*)array, bg);
-+  data((const char **)&array, 1);
-+}
-+
- /**  The destructor free all memory and server resources that are used by  the image. */
- Fl_RGB_Image::~Fl_RGB_Image() {
-   uncache();
-Index: fltk-1.3.x-r8772/FL/Fl_Image.H
-===================================================================
---- fltk-1.3.x-r8772/FL/Fl_Image.H	(revision 8771)
-+++ fltk-1.3.x-r8772/FL/Fl_Image.H	(working copy)
-@@ -34,6 +34,7 @@
- #  include "Enumerations.H"
- 
- class Fl_Widget;
-+class Fl_Pixmap;
- struct Fl_Menu_Item;
- struct Fl_Label;
- 
-@@ -196,6 +197,7 @@
- /**  The constructor creates a new image from the specified data. */
-   Fl_RGB_Image(const uchar *bits, int W, int H, int D=3, int LD=0) :
-     Fl_Image(W,H,D), array(bits), alloc_array(0), id_(0), mask_(0) {data((const char **)&array, 1); ld(LD);}
-+  Fl_RGB_Image(const Fl_Pixmap *pxm, Fl_Color bg=FL_GRAY);
-   virtual ~Fl_RGB_Image();
-   virtual Fl_Image *copy(int W, int H);
-   Fl_Image *copy() { return copy(w(), h()); }
-Index: fltk-1.3.x-r8772/src/fl_draw_pixmap.cxx
-===================================================================
---- fltk-1.3.x-r8772/src/fl_draw_pixmap.cxx	(revision 8771)
-+++ fltk-1.3.x-r8772/src/fl_draw_pixmap.cxx	(working copy)
-@@ -67,99 +67,6 @@
-   return 1;
- }
- 
--#ifdef U64
--
--// The callback from fl_draw_image to get a row of data passes this:
--struct pixmap_data {
--  int w, h;
--  const uchar*const* data;
--  union {
--    U64 colors[256];
--    U64* byte1[256];
--  };
--};
--
--// callback for 1 byte per pixel:
--static void cb1(void*v, int x, int y, int w, uchar* buf) {
--  pixmap_data& d = *(pixmap_data*)v;
--  const uchar* p = d.data[y]+x;
--  U64* q = (U64*)buf;
--  for (int X=w; X>0; X-=2, p += 2) {
--    if (X>1) {
--#  if WORDS_BIGENDIAN
--      *q++ = (d.colors[p[0]]<<32) | d.colors[p[1]];
--#  else
--      *q++ = (d.colors[p[1]]<<32) | d.colors[p[0]];
--#  endif
--    } else {
--#  if WORDS_BIGENDIAN
--      *q++ = d.colors[p[0]]<<32;
--#  else
--      *q++ = d.colors[p[0]];
--#  endif
--    }
--  }
--}
--
--// callback for 2 bytes per pixel:
--static void cb2(void*v, int x, int y, int w, uchar* buf) {
--  pixmap_data& d = *(pixmap_data*)v;
--  const uchar* p = d.data[y]+2*x;
--  U64* q = (U64*)buf;
--  for (int X=w; X>0; X-=2) {
--    U64* colors = d.byte1[*p++];
--    int index = *p++;
--    if (X>1) {
--      U64* colors1 = d.byte1[*p++];
--      int index1 = *p++;
--#  if WORDS_BIGENDIAN
--      *q++ = (colors[index]<<32) | colors1[index1];
--#  else
--      *q++ = (colors1[index1]<<32) | colors[index];
--#  endif
--    } else {
--#  if WORDS_BIGENDIAN
--      *q++ = colors[index]<<32;
--#  else
--      *q++ = colors[index];
--#  endif
--    }
--  }
--}
--
--#else // U32
--
--// The callback from fl_draw_image to get a row of data passes this:
--struct pixmap_data {
--  int w, h;
--  const uchar*const* data;
--  union {
--    U32 colors[256];
--    U32* byte1[256];
--  };
--};
--
--// callback for 1 byte per pixel:
--static void cb1(void*v, int x, int y, int w, uchar* buf) {
--  pixmap_data& d = *(pixmap_data*)v;
--  const uchar* p = d.data[y]+x;
--  U32* q = (U32*)buf;
--  for (int X=w; X--;) *q++ = d.colors[*p++];
--}
--
--// callback for 2 bytes per pixel:
--static void cb2(void*v, int x, int y, int w, uchar* buf) {
--  pixmap_data& d = *(pixmap_data*)v;
--  const uchar* p = d.data[y]+2*x;
--  U32* q = (U32*)buf;
--  for (int X=w; X--;) {
--    U32* colors = d.byte1[*p++];
--    *q++ = colors[*p++];
--  }
--}
--
--#endif // U64 else U32
--
- uchar **fl_mask_bitmap; // if non-zero, create bitmap and store pointer here
- 
- /**
-@@ -209,34 +116,33 @@
- }
- #endif
- 
--/**
--  Draw XPM image data, with the top-left corner at the given position.
--  \see fl_draw_pixmap(char* const* data, int x, int y, Fl_Color bg)
--  */
--int fl_draw_pixmap(const char*const* cdata, int x, int y, Fl_Color bg) {
--  pixmap_data d;
--  if (!fl_measure_pixmap(cdata, d.w, d.h)) return 0;
-+int fl_convert_pixmap(const char*const* cdata, uchar* out, Fl_Color bg) {
-+  int w, h;
-   const uchar*const* data = (const uchar*const*)(cdata+1);
-   int transparent_index = -1;
-   uchar *transparent_c = (uchar *)0; // such that transparent_c[0,1,2] are the RGB of the transparent color
-+
-+  if (!fl_measure_pixmap(cdata, w, h))
-+    return 0;
-+
-+  if ((chars_per_pixel < 1) || (chars_per_pixel > 2))
-+    return 0;
-+
-+  uchar colors[1<<(chars_per_pixel*8)][4];
-+
- #ifdef WIN32
-   color_count = 0;
-   used_colors = (uchar *)malloc(abs(ncolors)*3*sizeof(uchar));
- #endif
- 
--  if (ncolors < 0) {	// FLTK (non standard) compressed colormap
-+  if (ncolors < 0) {
-+    // FLTK (non standard) compressed colormap
-     ncolors = -ncolors;
-     const uchar *p = *data++;
-     // if first color is ' ' it is transparent (put it later to make
-     // it not be transparent):
-     if (*p == ' ') {
--      uchar* c = (uchar*)&d.colors[(int)' '];
--#ifdef U64
--      *(U64*)c = 0;
--#  if WORDS_BIGENDIAN
--      c += 4;
--#  endif
--#endif
-+      uchar* c = colors[(int)' '];
-       transparent_index = ' ';
-       Fl::get_color(bg, c[0], c[1], c[2]); c[3] = 0;
-       transparent_c = c;
-@@ -245,13 +151,7 @@
-     }
-     // read all the rest of the colors:
-     for (int i=0; i < ncolors; i++) {
--      uchar* c = (uchar*)&d.colors[*p++];
--#ifdef U64
--      *(U64*)c = 0;
--#  if WORDS_BIGENDIAN
--      c += 4;
--#  endif
--#endif
-+      uchar* c = colors[*p++];
- #ifdef WIN32
-       used_colors[3*color_count] = *p;
-       used_colors[3*color_count+1] = *(p+1);
-@@ -261,75 +161,49 @@
-       *c++ = *p++;
-       *c++ = *p++;
-       *c++ = *p++;
--#ifdef __APPLE_QUARTZ__
-       *c = 255;
--#else
--      *c = 0;
--#endif
-     }
--  } else {	// normal XPM colormap with names
--    if (chars_per_pixel>1) memset(d.byte1, 0, sizeof(d.byte1));
-+  } else {
-+    // normal XPM colormap with names
-     for (int i=0; i<ncolors; i++) {
-       const uchar *p = *data++;
-       // the first 1 or 2 characters are the color index:
-       int ind = *p++;
-       uchar* c;
--      if (chars_per_pixel>1) {
--#ifdef U64
--	U64* colors = d.byte1[ind];
--	if (!colors) colors = d.byte1[ind] = new U64[256];
--#else
--	U32* colors = d.byte1[ind];
--	if (!colors) colors = d.byte1[ind] = new U32[256];
--#endif
--	c = (uchar*)&colors[*p];
--	ind = (ind<<8)|*p++;
--      } else {
--	c = (uchar *)&d.colors[ind];
--      }
-+      if (chars_per_pixel>1)
-+        ind = (ind<<8)|*p++;
-+      c = colors[ind];
-       // look for "c word", or last word if none:
-       const uchar *previous_word = p;
-       for (;;) {
--	while (*p && isspace(*p)) p++;
--	uchar what = *p++;
--	while (*p && !isspace(*p)) p++;
--	while (*p && isspace(*p)) p++;
--	if (!*p) {p = previous_word; break;}
--	if (what == 'c') break;
--	previous_word = p;
--	while (*p && !isspace(*p)) p++;
-+        while (*p && isspace(*p)) p++;
-+        uchar what = *p++;
-+        while (*p && !isspace(*p)) p++;
-+        while (*p && isspace(*p)) p++;
-+        if (!*p) {p = previous_word; break;}
-+        if (what == 'c') break;
-+        previous_word = p;
-+        while (*p && !isspace(*p)) p++;
-       }
--#ifdef U64
--      *(U64*)c = 0;
--#  if WORDS_BIGENDIAN
--      c += 4;
--#  endif
--#endif
--#ifdef __APPLE_QUARTZ__
--      c[3] = 255;
--#endif
-       int parse = fl_parse_color((const char*)p, c[0], c[1], c[2]);
-+      c[3] = 255;
-       if (parse) {
- #ifdef WIN32
--	used_colors[3*color_count] = c[0];
--	used_colors[3*color_count+1] = c[1];
--	used_colors[3*color_count+2] = c[2];
--	color_count++;
-+        used_colors[3*color_count] = c[0];
-+        used_colors[3*color_count+1] = c[1];
-+        used_colors[3*color_count+2] = c[2];
-+        color_count++;
- #endif
--	}
--      else {
-+      } else {
-         // assume "None" or "#transparent" for any errors
--	// "bg" should be transparent...
--	Fl::get_color(bg, c[0], c[1], c[2]);
--#ifdef __APPLE_QUARTZ__
-+        // "bg" should be transparent...
-+        Fl::get_color(bg, c[0], c[1], c[2]);
-         c[3] = 0;
--#endif
--	transparent_index = ind;
--	transparent_c = c;
-+        transparent_index = ind;
-+        transparent_c = c;
-       }
-     }
-   }
--  d.data = data;
- #ifdef WIN32
-   if (transparent_c) {
-     make_unused_color(transparent_c[0], transparent_c[1], transparent_c[2]);
-@@ -339,88 +213,85 @@
-     make_unused_color(r, g, b);
-   }
- #endif
-+
-+  U32 *q = (U32*)out;
-+  for (int Y = 0; Y < h; Y++) {
-+    const uchar* p = data[Y];
-+    if (chars_per_pixel <= 1) {
-+      for (int X = 0; X < w; X++)
-+        memcpy(q++, colors[*p++], 4);
-+    } else {
-+      for (int X = 0; X < w; X++) {
-+        int ind = (*p++)<<8;
-+        ind |= *p++;
-+        memcpy(q++, colors[ind], 4);
-+      }
-+    }
-+  }
-   
-+  return 1;
-+}
-+
-+/**
-+  Draw XPM image data, with the top-left corner at the given position.
-+  \see fl_draw_pixmap(char* const* data, int x, int y, Fl_Color bg)
-+  */
-+int fl_draw_pixmap(const char*const* cdata, int x, int y, Fl_Color bg) {
-+  int w, h;
-+
-+  if (!fl_measure_pixmap(cdata, w, h))
-+    return 0;
-+
-+  uchar buffer[w*h*4];
-+
-+  if (!fl_convert_pixmap(cdata, buffer, bg))
-+    return 0;
-+
-+  // FIXME: Hack until fl_draw_image() supports alpha properly
- #ifdef  __APPLE_QUARTZ__
-   if (fl_graphics_driver->class_name() == Fl_Quartz_Graphics_Driver::class_id ) {
--    bool transparent = (transparent_index>=0);
--    transparent = true;
--    U32 *array = new U32[d.w * d.h], *q = array;
--    for (int Y = 0; Y < d.h; Y++) {
--      const uchar* p = data[Y];
--      if (chars_per_pixel <= 1) {
--	for (int X = 0; X < d.w; X++) {
--	  *q++ = d.colors[*p++];
--	}
--      } else {
--	for (int X = 0; X < d.w; X++) {
--	  U32* colors = (U32*)d.byte1[*p++];
--	  *q++ = colors[*p++];
--	}
--      }
--    }
-     CGColorSpaceRef lut = CGColorSpaceCreateDeviceRGB();
--    CGDataProviderRef src = CGDataProviderCreateWithData( 0L, array, d.w * d.h * 4, 0L);
--    CGImageRef img = CGImageCreate(d.w, d.h, 8, 4*8, 4*d.w,
--				   lut, transparent?kCGImageAlphaLast:kCGImageAlphaNoneSkipLast,
--				   src, 0L, false, kCGRenderingIntentDefault);
-+    CGDataProviderRef src = CGDataProviderCreateWithData( 0L, buffer, w * h * 4, 0L);
-+    CGImageRef img = CGImageCreate(w, h, 8, 4*8, 4*w,
-+                                   lut, kCGImageAlphaLast,
-+                                   src, 0L, false, kCGRenderingIntentDefault);
-     CGColorSpaceRelease(lut);
-     CGDataProviderRelease(src);
--    CGRect rect = { { x, y} , { d.w, d.h } };
--    Fl_X::q_begin_image(rect, 0, 0, d.w, d.h);
-+    CGRect rect = { { x, y }, { w, h } };
-+    Fl_X::q_begin_image(rect, 0, 0, w, h);
-     CGContextDrawImage(fl_gc, rect, img);
-     Fl_X::q_end_image();
-     CGImageRelease(img);
--    delete[] array;
--    }
--  else {
-+  } else {
- #endif // __APPLE_QUARTZ__
--
-   // build the mask bitmap used by Fl_Pixmap:
--  if (fl_mask_bitmap && transparent_index >= 0) {
--    int W = (d.w+7)/8;
--    uchar* bitmap = new uchar[W * d.h];
-+  if (fl_mask_bitmap) {
-+    int W = (w+7)/8;
-+    uchar* bitmap = new uchar[W * h];
-     *fl_mask_bitmap = bitmap;
--    for (int Y = 0; Y < d.h; Y++) {
--      const uchar* p = data[Y];
--      if (chars_per_pixel <= 1) {
--	int dw = d.w;
--	for (int X = 0; X < W; X++) {
--	  uchar b = (dw-->0 && *p++ != transparent_index);
--	  if (dw-->0 && *p++ != transparent_index) b |= 2;
--	  if (dw-->0 && *p++ != transparent_index) b |= 4;
--	  if (dw-->0 && *p++ != transparent_index) b |= 8;
--	  if (dw-->0 && *p++ != transparent_index) b |= 16;
--	  if (dw-->0 && *p++ != transparent_index) b |= 32;
--	  if (dw-->0 && *p++ != transparent_index) b |= 64;
--	  if (dw-->0 && *p++ != transparent_index) b |= 128;
--	  *bitmap++ = b;
--	}
--      } else {
--        uchar b = 0, bit = 1;
--	for (int X = 0; X < d.w; X++) {
--	  int ind = *p++;
--	  ind = (ind<<8) | (*p++);
--	  if (ind != transparent_index) b |= bit;
--
--          if (bit < 128) bit <<= 1;
--	  else {
--	    *bitmap++ = b;
--	    b = 0;
--	    bit = 1;
--	  }
--	}
--
--        if (bit > 1) *bitmap++ = b;
-+    const uchar *p = &buffer[3];
-+    for (int Y = 0; Y < h; Y++) {
-+      int dw = w;
-+      for (int X = 0; X < W; X++) {
-+        uchar b = 0;
-+        for (int bit = 0x01;bit <= 0x80;bit<<=1) {
-+          if (dw-- < 0)
-+            break;
-+          if (*p > 127)
-+            b |= bit;
-+          p += 4;
-+        }
-+        *bitmap++ = b;
-       }
-     }
-   }
- 
--  fl_draw_image(chars_per_pixel==1 ? cb1 : cb2, &d, x, y, d.w, d.h, 4);
-+  fl_draw_image(buffer, x, y, w, h, 4);
-+
- #ifdef __APPLE_QUARTZ__
-     }
- #endif
- 
--  if (chars_per_pixel > 1) for (int i = 0; i < 256; i++) delete[] d.byte1[i];
-   return 1;
- }
- 
-diff -up fltk-1.3.x-r8772/configh.in.cursor fltk-1.3.x-r8772/configh.in
---- fltk-1.3.x-r8772/configh.in.cursor	2011-06-08 18:23:14.000000000 +0200
-+++ fltk-1.3.x-r8772/configh.in	2011-06-08 18:24:34.373649514 +0200
-@@ -125,6 +125,14 @@
- #define HAVE_XFIXES 0
- 
- /*
-+ * HAVE_XCURSOR:
-+ *
-+ * Do we have the X cursor library?
++ 
++ #define HAVE_XCURSOR 0
++ 
++ /*
+   * __APPLE_QUARTZ__:
+   *
+*** fltk-1.3.0/configure.in	2011-03-06 10:54:58.000000000 -0600
+--- fltk/configure.in	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 875,878 ****
+--- 875,880 ----
+          # MacOS X uses Cocoa for graphics.
+          LIBS="$LIBS -framework Cocoa"
++         # And some Carbon for keyboard handling
++         LIBS="$LIBS -framework Carbon"
+  
+  	if test x$have_pthread = xyes; then
+***************
+*** 1007,1010 ****
+--- 1009,1032 ----
+  	fi
+  
++ 	dnl Check for the Xfixes extension unless disabled...
++         AC_ARG_ENABLE(xfixes, [  --enable-xfixes       turn on Xfixes support [default=yes]])
++ 
++ 	if test x$enable_xfixes != xno; then
++ 	    AC_CHECK_HEADER(X11/extensions/Xfixes.h, AC_DEFINE(HAVE_XFIXES),,
++ 	        [#include <X11/Xlib.h>])
++ 	    AC_CHECK_LIB(Xfixes, XFixesQueryExtension,
++ 		LIBS="-lXfixes $LIBS")
++ 	fi
++ 
++ 	dnl Check for the Xcursor library unless disabled...
++         AC_ARG_ENABLE(xcursor, [  --enable-xcursor        turn on Xcursor support [default=yes]])
++ 
++ 	if test x$enable_xcursor != xno; then
++ 	    AC_CHECK_HEADER(X11/Xcursor/Xcursor.h, AC_DEFINE(HAVE_XCURSOR),,
++ 	        [#include <X11/Xlib.h>])
++ 	    AC_CHECK_LIB(Xcursor, XcursorImageCreate,
++ 		LIBS="-lXcursor $LIBS")
++ 	fi
++ 
+  	dnl Check for overlay visuals...
+  	AC_PATH_PROG(XPROP, xprop)
+*** fltk-1.3.0/documentation/src/enumerations.dox	2011-05-11 10:49:30.000000000 -0500
+--- fltk/documentation/src/enumerations.dox	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 58,61 ****
+--- 58,62 ----
+      data. 
+  \li FL_DND_RELEASE - Dragged data is about to be dropped. 
++ \li FL_FULLSCREEN - The fullscreen state of the window has changed.
+  
+  
+*** fltk-1.3.0/documentation/src/events.dox	2011-05-11 10:49:30.000000000 -0500
+--- fltk/documentation/src/events.dox	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 301,304 ****
+--- 301,311 ----
+  the immediately following \p FL_PASTE event.
+  
++ \subsection events_fl_fullscreen FL_FULLSCREEN
++ 
++ The application window has been changed from normal to fullscreen, or
++ from fullscreen to normal. If you are using a X window manager which
++ supports Extended Window Manager Hints, this event will not be
++ delivered until the change has actually happened. 
++ 
+  
+  \section events_event_xxx Fl::event_*() methods
+*** fltk-1.3.0/src/Fl.cxx	2011-05-23 11:49:02.000000000 -0500
+--- fltk-1.3.0.new/src/Fl.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 80,83 ****
+--- 80,85 ----
+  #endif // WIN32
+  
++ extern void fl_update_focus(void);
++ 
+  //
+  // Globals...
+***************
+*** 445,448 ****
+--- 447,513 ----
+  
+  ////////////////////////////////////////////////////////////////
++ // Clipboard notifications
++ 
++ struct Clipboard_Notify {
++   Fl_Clipboard_Notify_Handler handler;
++   void *data;
++   struct Clipboard_Notify *next;
++ };
++ 
++ static struct Clipboard_Notify *clip_notify_list = NULL;
++ 
++ extern void fl_clipboard_notify_change(); // in Fl_<platform>.cxx
++ 
++ void Fl::add_clipboard_notify(Fl_Clipboard_Notify_Handler h, void *data) {
++   struct Clipboard_Notify *node;
++ 
++   remove_clipboard_notify(h);
++ 
++   node = new Clipboard_Notify;
++ 
++   node->handler = h;
++   node->data = data;
++   node->next = clip_notify_list;
++ 
++   clip_notify_list = node;
++ 
++   fl_clipboard_notify_change();
++ }
++ 
++ void Fl::remove_clipboard_notify(Fl_Clipboard_Notify_Handler h) {
++   struct Clipboard_Notify *node, **prev;
++ 
++   node = clip_notify_list;
++   prev = &clip_notify_list;
++   while (node != NULL) {
++     if (node->handler == h) {
++       *prev = node->next;
++       delete node;
++ 
++       fl_clipboard_notify_change();
++ 
++       return;
++     }
++ 
++     prev = &node->next;
++     node = node->next;
++   }
++ }
++ 
++ bool fl_clipboard_notify_empty(void) {
++   return clip_notify_list == NULL;
++ }
++ 
++ void fl_trigger_clipboard_notify(int source) {
++   struct Clipboard_Notify *node;
++ 
++   node = clip_notify_list;
++   while (node != NULL) {
++     node->handler(source, node->data);
++     node = node->next;
++   }
++ }
++ 
++ ////////////////////////////////////////////////////////////////
+  // wait/run/check/ready:
+  
+***************
+*** 881,884 ****
+--- 946,951 ----
+      }
+      e_number = old_event;
++     // let the platform code do what it needs
++     fl_update_focus();
+    }
+  }
+***************
+*** 1362,1366 ****
+  // hide() destroys the X window, it does not do unmap!
+  
+! #if !defined(WIN32) && USE_XFT
+  extern void fl_destroy_xft_draw(Window);
+  #endif
+--- 1429,1436 ----
+  // hide() destroys the X window, it does not do unmap!
+  
+! #if defined(WIN32)
+! extern void fl_clipboard_notify_untarget(HWND wnd);
+! extern void fl_update_clipboard(void);
+! #elif USE_XFT
+  extern void fl_destroy_xft_draw(Window);
+  #endif
+***************
+*** 1409,1420 ****
+    // this little trick keeps the current clipboard alive, even if we are about
+    // to destroy the window that owns the selection.
+!   if (GetClipboardOwner()==ip->xid) {
+!     Fl_Window *w1 = Fl::first_window();
+!     if (w1 && OpenClipboard(fl_xid(w1))) {
+!       EmptyClipboard();
+!       SetClipboardData(CF_TEXT, NULL);
+!       CloseClipboard();
+!     }
+!   }
+    // Send a message to myself so that I'll get out of the event loop...
+    PostMessage(ip->xid, WM_APP, 0, 0);
+--- 1479,1486 ----
+    // this little trick keeps the current clipboard alive, even if we are about
+    // to destroy the window that owns the selection.
+!   if (GetClipboardOwner()==ip->xid)
+!     fl_update_clipboard();
+!   // Make sure we unlink this window from the clipboard chain
+!   fl_clipboard_notify_untarget(ip->xid);
+    // Send a message to myself so that I'll get out of the event loop...
+    PostMessage(ip->xid, WM_APP, 0, 0);
+*** fltk-1.3.0/src/Fl_Image.cxx	2011-04-20 09:01:04.000000000 -0500
+--- fltk-1.3.0.new/src/Fl_Image.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 173,176 ****
+--- 173,189 ----
+  // RGB image class...
+  //
++ 
++ int fl_convert_pixmap(const char*const* cdata, uchar* out, Fl_Color bg);
++ 
++ /** The constructor creates a new RGBA image from the specified Fl_Pixmap. */
++ Fl_RGB_Image::Fl_RGB_Image(const Fl_Pixmap *pxm, Fl_Color bg):
++   Fl_Image(pxm->w(), pxm->h(), 4), id_(0), mask_(0)
++ {
++   array = new uchar[w() * h() * d()];
++   alloc_array = 1;
++   fl_convert_pixmap(pxm->data(), (uchar*)array, bg);
++   data((const char **)&array, 1);
++ }
++ 
+  /**  The destructor free all memory and server resources that are used by  the image. */
+  Fl_RGB_Image::~Fl_RGB_Image() {
+*** fltk-1.3.0/src/Fl_Window.cxx	2011-02-25 02:44:47.000000000 -0600
+--- fltk-1.3.0.new/src/Fl_Window.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 60,63 ****
+--- 60,67 ----
+    size_range_set = 0;
+    minw = maxw = minh = maxh = 0;
++   no_fullscreen_x = 0;
++   no_fullscreen_y = 0;
++   no_fullscreen_w = w();
++   no_fullscreen_h = h();
+    callback((Fl_Callback*)default_callback);
+  }
+***************
+*** 66,71 ****
+  : Fl_Group(X, Y, W, H, l) {
+    cursor_default = FL_CURSOR_DEFAULT;
+-   cursor_fg      = FL_BLACK;
+-   cursor_bg      = FL_WHITE;
+  
+    _Fl_Window();
+--- 70,73 ----
+***************
+*** 77,82 ****
+    : Fl_Group((Fl_Group::current(0),0), 0, W, H, l) {
+    cursor_default = FL_CURSOR_DEFAULT;
+-   cursor_fg      = FL_BLACK;
+-   cursor_bg      = FL_WHITE;
+  
+    _Fl_Window();
+--- 79,82 ----
+*** fltk-1.3.0/src/Fl_Window_fullscreen.cxx	2011-03-12 15:36:21.000000000 -0600
+--- fltk-1.3.0.new/src/Fl_Window_fullscreen.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 61,97 ****
+  }
+  
+  void Fl_Window::fullscreen() {
+! #ifndef WIN32
+!   //this would clobber the fake wm, since it relies on the border flags to
+!   //determine its thickness
+!   border(0);
+! #endif
+! #if defined(__APPLE__) || defined(WIN32) || defined(USE_X11)
+!   int sx, sy, sw, sh;
+!   Fl::screen_xywh(sx, sy, sw, sh, x(), y(), w(), h());
+!   // if we are on the main screen, we will leave the system menu bar unobstructed
+!   if (Fl::x()>=sx && Fl::y()>=sy && Fl::x()+Fl::w()<=sx+sw && Fl::y()+Fl::h()<=sy+sh) {
+!     sx = Fl::x(); sy = Fl::y(); 
+!     sw = Fl::w(); sh = Fl::h();
+    }
+-   if (x()==sx) x(sx+1); // make sure that we actually execute the resize
+- #if defined(USE_X11)
+-   resize(0, 0, w(), h()); // work around some quirks in X11
+- #endif
+-   resize(sx, sy, sw, sh);
+- #else
+-   if (!x()) x(1); // make sure that we actually execute the resize
+-   resize(0,0,Fl::w(),Fl::h());
+- #endif
+  }
+  
+  void Fl_Window::fullscreen_off(int X,int Y,int W,int H) {
+!   // this order produces less blinking on IRIX:
+!   resize(X,Y,W,H);
+! #ifndef WIN32
+!   border(1);
+! #endif
+  }
+  
+  //
+  // End of "$Id: Fl_Window_fullscreen.cxx 8515 2011-03-12 21:36:21Z manolo $".
+--- 61,106 ----
+  }
+  
++ void fullscreen_x(Fl_Window *w);
++ void fullscreen_off_x();
++ void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H);
++ 
++ /* Note: The previous implementation toggled border(). With this new
++    implementation this is not necessary. Additionally, if we do that,
++    the application may lose focus when switching out of fullscreen
++    mode with some window managers. Besides, the API does not say that
++    the FLTK border state should be toggled; it only says that the
++    borders should not be *visible*. 
 + */
-+
-+#define HAVE_XCURSOR 0
-+
-+/*
-  * __APPLE_QUARTZ__:
-  *
-  * All Apple implementations are now based on Quartz and Cocoa,
-diff -up fltk-1.3.x-r8772/configure.in.cursor fltk-1.3.x-r8772/configure.in
---- fltk-1.3.x-r8772/configure.in.cursor	2011-06-08 18:23:14.000000000 +0200
-+++ fltk-1.3.x-r8772/configure.in	2011-06-08 18:25:06.681678402 +0200
-@@ -1018,6 +1018,16 @@ case $uname_GUI in
- 		LIBS="-lXfixes $LIBS")
- 	fi
- 
-+	dnl Check for the Xcursor library unless disabled...
-+        AC_ARG_ENABLE(xcursor, [  --enable-xcursor        turn on Xcursor support [default=yes]])
-+
-+	if test x$enable_xcursor != xno; then
-+	    AC_CHECK_HEADER(X11/Xcursor/Xcursor.h, AC_DEFINE(HAVE_XCURSOR),,
-+	        [#include <X11/Xlib.h>])
-+	    AC_CHECK_LIB(Xcursor, XcursorImageCreate,
-+		LIBS="-lXcursor $LIBS")
-+	fi
-+
- 	dnl Check for overlay visuals...
- 	AC_PATH_PROG(XPROP, xprop)
- 	AC_CACHE_CHECK(for X overlay visuals, ac_cv_have_overlay,
-diff -up fltk-1.3.x-r8772/FL/Enumerations.H.cursor fltk-1.3.x-r8772/FL/Enumerations.H
---- fltk-1.3.x-r8772/FL/Enumerations.H.cursor	2011-06-08 18:23:14.285141149 +0200
-+++ fltk-1.3.x-r8772/FL/Enumerations.H	2011-06-08 18:23:14.308143306 +0200
-@@ -879,35 +879,36 @@ inline Fl_Color fl_color_cube(int r, int
- 
- /** The following constants define the mouse cursors that are available in FLTK.
- 
--    The double-headed arrows are bitmaps provided by FLTK on X, the others
--    are provided by system-defined cursors.
-+    Cursors are provided by the system when available, or bitmaps built into
-+    FLTK as a fallback.
- 
-     \todo enum Fl_Cursor needs maybe an image.
- */
- enum Fl_Cursor {
--  FL_CURSOR_DEFAULT	=  0, /**< the default cursor, usually an arrow. */
--  FL_CURSOR_ARROW	= 35, /**< an arrow pointer. */
--  FL_CURSOR_CROSS	= 66, /**< crosshair. */
--  FL_CURSOR_WAIT	= 76, /**< watch or hourglass. */
--  FL_CURSOR_INSERT	= 77, /**< I-beam. */
--  FL_CURSOR_HAND	= 31, /**< hand (uparrow on MSWindows). */
--  FL_CURSOR_HELP	= 47, /**< question mark. */
--  FL_CURSOR_MOVE	= 27, /**< 4-pointed arrow. */
--  // fltk provides bitmaps for these:
--  FL_CURSOR_NS		= 78, /**< up/down arrow. */
--  FL_CURSOR_WE		= 79, /**< left/right arrow. */
--  FL_CURSOR_NWSE	= 80, /**< diagonal arrow. */
--  FL_CURSOR_NESW	= 81, /**< diagonal arrow. */
--  FL_CURSOR_NONE	=255, /**< invisible. */
--  // for back compatibility (non MSWindows ones):
--  FL_CURSOR_N		= 70, /**< for back compatibility. */
--  FL_CURSOR_NE		= 69, /**< for back compatibility. */
--  FL_CURSOR_E		= 49, /**< for back compatibility. */
--  FL_CURSOR_SE		=  8, /**< for back compatibility. */
--  FL_CURSOR_S		=  9, /**< for back compatibility. */
--  FL_CURSOR_SW		=  7, /**< for back compatibility. */
--  FL_CURSOR_W		= 36, /**< for back compatibility. */
--  FL_CURSOR_NW		= 68 /**< for back compatibility. */
-+  FL_CURSOR_DEFAULT = 0,    /**< the default cursor, usually an arrow. */
-+  FL_CURSOR_ARROW   = 1,    /**< an arrow pointer. */
-+  FL_CURSOR_CROSS   = 2,    /**< crosshair. */
-+  FL_CURSOR_WAIT    = 3,    /**< busy indicator (e.g. hourglass). */
-+  FL_CURSOR_INSERT  = 4,    /**< I-beam. */
-+  FL_CURSOR_HAND    = 5,    /**< pointing hand. */
-+  FL_CURSOR_HELP    = 6,    /**< question mark pointer. */
-+  FL_CURSOR_MOVE    = 7,    /**< 4-pointed arrow or hand. */
-+
-+  /* Resize indicators */
-+  FL_CURSOR_NS      = 101,  /**< up/down resize. */
-+  FL_CURSOR_WE      = 102,  /**< left/right resize. */
-+  FL_CURSOR_NWSE    = 103,  /**< diagonal resize. */
-+  FL_CURSOR_NESW    = 104,  /**< diagonal resize. */
-+  FL_CURSOR_NE      = 110,  /**< upwards, right resize. */
-+  FL_CURSOR_N       = 111,  /**< upwards resize. */
-+  FL_CURSOR_NW      = 112,  /**< upwards, left resize. */
-+  FL_CURSOR_E       = 113,  /**< leftwards resize. */
-+  FL_CURSOR_W       = 114,  /**< rightwards resize. */
-+  FL_CURSOR_SE      = 115,  /**< downwards, right resize. */
-+  FL_CURSOR_S       = 116,  /**< downwards resize. */
-+  FL_CURSOR_SW      = 117,  /**< downwards, left resize. */
-+
-+  FL_CURSOR_NONE    = 255,  /**< invisible. */
- };
- /*@}*/		// group: Cursors  
- 
-diff -up fltk-1.3.x-r8772/FL/fl_draw.H.cursor fltk-1.3.x-r8772/FL/fl_draw.H
---- fltk-1.3.x-r8772/FL/fl_draw.H.cursor	2011-06-02 10:06:09.000000000 +0200
-+++ fltk-1.3.x-r8772/FL/fl_draw.H	2011-06-08 18:23:14.320144432 +0200
-@@ -757,7 +757,8 @@ FL_EXPORT const char* fl_shortcut_label(
- FL_EXPORT unsigned int fl_old_shortcut(const char* s);
- FL_EXPORT void fl_overlay_rect(int x,int y,int w,int h);
- FL_EXPORT void fl_overlay_clear();
--FL_EXPORT void fl_cursor(Fl_Cursor, Fl_Color fg=FL_BLACK, Fl_Color bg=FL_WHITE);
-+FL_EXPORT void fl_cursor(Fl_Cursor);
-+FL_EXPORT void fl_cursor(Fl_Cursor, Fl_Color fg, Fl_Color bg=FL_WHITE);
- FL_EXPORT const char* fl_expand_text(const char* from, char* buf, int maxbuf,
-                                      double maxw, int& n, double &width,
-                                      int wrap, int draw_symbols = 0);
-diff -up fltk-1.3.x-r8772/FL/Fl_Window.H.cursor fltk-1.3.x-r8772/FL/Fl_Window.H
---- fltk-1.3.x-r8772/FL/Fl_Window.H.cursor	2011-06-08 18:23:14.287141337 +0200
-+++ fltk-1.3.x-r8772/FL/Fl_Window.H	2011-06-08 18:23:50.721557098 +0200
-@@ -37,6 +37,7 @@
- #define FL_DOUBLE_WINDOW 0xF1   ///< double window type id
- 
- class Fl_X;
-+class Fl_RGB_Image;
- 
- /**
-   This widget produces an actual window.  This can either be a main
-@@ -72,7 +73,6 @@ class FL_EXPORT Fl_Window : public Fl_Gr
-   int no_fullscreen_x, no_fullscreen_y, no_fullscreen_w, no_fullscreen_h;
-   // cursor stuff
-   Fl_Cursor cursor_default;
--  Fl_Color cursor_fg, cursor_bg;
-   void size_range_();
-   void _Fl_Window(); // constructor innards
- 
-@@ -447,14 +447,17 @@ public:
-     is different.
- 
-     The type Fl_Cursor is an enumeration defined in <FL/Enumerations.H>.
--    (Under X you can get any XC_cursor value by passing 
--    Fl_Cursor((XC_foo/2)+1)).  The colors only work on X, they are
--    not implemented on WIN32.
- 
--    For back compatibility only.
-+    \see cursor(const Fl_RGB_Image*, int, int), default_cursor()
+  void Fl_Window::fullscreen() {
+!   if (shown() && !(flags() & Fl_Widget::FULLSCREEN)) {
+!     no_fullscreen_x = x();
+!     no_fullscreen_y = y();
+!     no_fullscreen_w = w();
+!     no_fullscreen_h = h();
+!     fullscreen_x(this);
+!   } else {
+!     set_flag(FULLSCREEN);
+    }
+  }
+  
+  void Fl_Window::fullscreen_off(int X,int Y,int W,int H) {
+!   if (shown() && (flags() & Fl_Widget::FULLSCREEN)) {
+!     fullscreen_off_x(this, X, Y, W, H);
+!   } else {
+!     clear_flag(FULLSCREEN);
+!   }
+!   no_fullscreen_x = no_fullscreen_y = no_fullscreen_w = no_fullscreen_h = 0;
+! }
+! 
+! void Fl_Window::fullscreen_off() {
+!   if (!no_fullscreen_x && !no_fullscreen_y) {
+!     // Window was initially created fullscreen - default to current monitor
+!     no_fullscreen_x = x();
+!     no_fullscreen_y = y();
+!   }
+!   fullscreen_off(no_fullscreen_x, no_fullscreen_y, no_fullscreen_w, no_fullscreen_h);
+  }
+  
++ 
+  //
+  // End of "$Id: Fl_Window_fullscreen.cxx 8515 2011-03-12 21:36:21Z manolo $".
+*** fltk-1.3.0/src/Fl_cocoa.mm	2011-06-16 07:35:32.000000000 -0500
+--- fltk-1.3.0.new/src/Fl_cocoa.mm	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 62,65 ****
+--- 62,66 ----
+  
+  #import <Cocoa/Cocoa.h>
++ #import <Carbon/Carbon.h>
+  
+  #ifndef NSINTEGER_DEFINED // appears with 10.5 in NSObjCRuntime.h
+***************
+*** 108,112 ****
+  void *fl_system_menu;                   // this is really a NSMenu*
+  Fl_Sys_Menu_Bar *fl_sys_menu_bar = 0;
+- void *fl_default_cursor;		// this is really a NSCursor*
+  void *fl_capture = 0;			// (NSWindow*) we need this to compensate for a missing(?) mouse capture
+  bool fl_show_iconic;                    // true if called from iconize() - shows the next created window in collapsed state
+--- 109,112 ----
+***************
+*** 125,128 ****
+--- 125,130 ----
+  #endif
+  
++ bool use_simple_keyboard = false;
++ 
+  enum { FLTKTimerEvent = 1, FLTKDataReadyEvent };
+  
+***************
+*** 141,144 ****
+--- 143,179 ----
+  }
+  
++ // Undocumented voodoo. Taken from Mozilla.
++ #define ENABLE_ROMAN_KYBDS_ONLY -23
++ 
++ void fl_update_focus(void)
++ {
++   Fl_Widget *focus;
++ 
++   focus = Fl::grab();
++   if (!focus)
++     focus = Fl::focus();
++   if (!focus)
++     return;
++ 
++   if (focus->simple_keyboard())
++     use_simple_keyboard = true;
++   else
++     use_simple_keyboard = false;
++ 
++   // Force a "Roman" or "ASCII" keyboard, which both the Mozilla and
++   // Safari people seem to think implies turning off advanced IME stuff
++   // (see nsTSMManager::SyncKeyScript in Mozilla and enableSecureTextInput
++   // in Safari/Webcore). Should be good enough for us then...
++ #if (MAC_OS_X_VERSION_MIN_REQUIRED >= MAC_OS_X_VERSION_10_5)
++   CFArrayRef inputSources = TISCreateASCIICapableInputSourceList();
++   TSMSetDocumentProperty(TSMGetActiveDocument(),
++                          kTSMDocumentEnabledInputSourcesPropertyTag,
++                          sizeof(CFArrayRef), &inputSources);
++   CFRelease(inputSources);
++ #else
++   KeyScript(use_simple_keyboard ? ENABLE_ROMAN_KYBDS_ONLY : smKeyEnableKybds);
++ #endif  
++ }
++ 
+  /*
+   * Mac keyboard lookup table
+***************
+*** 615,618 ****
+--- 650,657 ----
+    containsGLsubwindow = contains;
+  }
++ - (BOOL)canBecomeKeyWindow
++ {
++   return YES;
++ }
+  @end
+  
+***************
+*** 844,847 ****
+--- 883,905 ----
+  @end
+  
++ static const char* cocoaDead2FLTK(const char *in)
++ {
++   if (strcmp(in, "\140") == 0)      // GRAVE ACCENT
++     return "\314\200";              // COMBINING GRAVE ACCENT
++   if (strcmp(in, "\302\264") == 0)  // ACUTE ACCENT
++     return "\314\201";              // COMBINING ACUTE ACCENT
++   if (strcmp(in, "\136") == 0)      // CIRCUMFLEX ACCENT
++     return "\314\202";              // COMBINING CIRCUMFLEX ACCENT
++   if (strcmp(in, "\176") == 0)      // TILDE
++     return "\314\203";              // COMBINING TILDE
++   if (strcmp(in, "\302\250") == 0)  // DIAERESIS
++     return "\314\210";              // COMBINING DIAERESIS
++   // FIXME: OS X dead key behaviour isn't documented and I don't have
++   //        any more keyboards to test with...
++ 
++   // hope that OS X gave us something proper to begin with
++   return in;
++ }
++ 
+  /*
+  Handle cocoa keyboard events
+***************
+*** 1034,1037 ****
+--- 1092,1099 ----
+    FLWindow *nsw = (FLWindow*)[notif object];
+    Fl_Window *window = [nsw getFl_Window];
++   /* Fullscreen windows obscure all other windows so we need to return
++      to a "normal" level when the user switches to another window */
++   if (window->fullscreen_active())
++     [nsw setLevel:NSNormalWindowLevel];
+    Fl::handle( FL_UNFOCUS, window);
+    fl_unlock_function();
+***************
+*** 1042,1045 ****
+--- 1104,1110 ----
+    FLWindow *nsw = (FLWindow*)[notif object];
+    Fl_Window *w = [nsw getFl_Window];
++   /* Restore previous fullscreen level */
++   if (w->fullscreen_active())
++     [nsw setLevel:NSStatusWindowLevel];
+    if ( w->border() || (!w->modal() && !w->tooltip_window()) ) Fl::handle( FL_FOCUS, w);
+    fl_unlock_function();
+***************
+*** 1229,1235 ****
+--- 1294,1304 ----
+  @end
+  
++ static void clipboard_check(void);
++ 
+  @implementation FLApplication
+  + (void)sendEvent:(NSEvent *)theEvent
+  {
++   // update clipboard status
++   clipboard_check();
+    NSEventType type = [theEvent type];  
+    if (type == NSLeftMouseDown) {
+***************
+*** 1286,1291 ****
+      while (ign_event);
+      
+-     fl_default_cursor = [NSCursor arrowCursor];
+- 
+      // bring the application into foreground without a 'CARB' resource
+      Boolean same_psn;
+--- 1355,1358 ----
+***************
+*** 1587,1590 ****
+--- 1654,1658 ----
+  - (BOOL)acceptsFirstResponder;
+  - (BOOL)acceptsFirstMouse:(NSEvent*)theEvent;
++ - (void)resetCursorRects;
+  - (BOOL)performKeyEquivalent:(NSEvent*)theEvent;
+  - (void)mouseUp:(NSEvent *)theEvent;
+***************
+*** 1644,1647 ****
+--- 1712,1725 ----
+    return (first == w || !first->modal());
+  }
++ - (void)resetCursorRects {
++   Fl_Window *w = [(FLWindow*)[self window] getFl_Window];
++   Fl_X *i = Fl_X::i(w);
++   // We have to have at least one cursor rect for invalidateCursorRectsForView
++   // to work, hence the "else" clause.
++   if (i->cursor)
++     [self addCursorRect:[self visibleRect] cursor:(NSCursor*)i->cursor];
++   else
++     [self addCursorRect:[self visibleRect] cursor:[NSCursor arrowCursor]];
++ }
+  - (void)mouseUp:(NSEvent *)theEvent {
+    cocoaMouseHandler(theEvent);
+***************
+*** 1703,1708 ****
+      }
+    }
+    if (!no_text_key && !(Fl::e_state & FL_META) ) {
+!     // Don't send cmd-<key> to interpretKeyEvents because it beeps.
+      // Then we can let the OS have a stab at it and see if it thinks it
+      // should result in some text
+--- 1781,1791 ----
+      }
+    }
++   // Don't send cmd-<key> to interpretKeyEvents because it beeps.
+    if (!no_text_key && !(Fl::e_state & FL_META) ) {
+!     // The simple keyboard model will ignore insertText, so we need to grab
+!     // the symbol directly from the event. Note that we still use setMarkedText.
+!     if (use_simple_keyboard)
+!       [FLView prepareEtext:[theEvent charactersIgnoringModifiers]];
+! 
+      // Then we can let the OS have a stab at it and see if it thinks it
+      // should result in some text
+***************
+*** 1883,1901 ****
+  
+    if (!in_key_event) fl_lock_function();
+    [FLView prepareEtext:received];
+    // We can get called outside of key events (e.g. from the character
+!   // palette). Transform such actions to FL_PASTE events.
+    if (!in_key_event) {
+      Fl_Window *target = [(FLWindow*)[self window] getFl_Window];
+!     Fl::handle(FL_PASTE, target);
+      // for some reason, the window does not redraw until the next mouse move or button push
+      // sending a 'redraw()' or 'awake()' does not solve the issue!
+      Fl::flush();
+    }
+    if (!in_key_event) fl_unlock_function();
+  }
+  
+  - (void)setMarkedText:(id)aString selectedRange:(NSRange)newSelection  {
+!   NSString *received;
+    if (newSelection.location == 0) {
+      [self unmarkText];
+--- 1966,1993 ----
+  
+    if (!in_key_event) fl_lock_function();
++ 
++   // Simple keyboard widgets do not want these side channel inputs.
++   if (use_simple_keyboard)
++     goto end;
++ 
+    [FLView prepareEtext:received];
++ 
+    // We can get called outside of key events (e.g. from the character
+!   // palette). We need to fake our own key event at that point.
+    if (!in_key_event) {
+      Fl_Window *target = [(FLWindow*)[self window] getFl_Window];
+!     Fl::e_keysym = Fl::e_original_keysym = 0;
+!     Fl::handle(FL_KEYDOWN, target);
+      // for some reason, the window does not redraw until the next mouse move or button push
+      // sending a 'redraw()' or 'awake()' does not solve the issue!
+      Fl::flush();
+    }
++ 
++ end:
+    if (!in_key_event) fl_unlock_function();
+  }
+  
+  - (void)setMarkedText:(id)aString selectedRange:(NSRange)newSelection  {
+!   NSString *received, *current, *aggregate;
+    if (newSelection.location == 0) {
+      [self unmarkText];
+***************
+*** 1908,1916 ****
+    }
+    //NSLog(@"setMarkedText: %@ %d %d",received,newSelection.location,newSelection.length);
+    // This code creates the OS X behaviour of seeing dead keys as things
+    // are being composed.
+    next_compose_length = newSelection.location;
+!   [FLView prepareEtext:received];
+!   //NSLog(@"Fl::e_text=%@ Fl::e_length=%d next_compose_length=%d", received, Fl::e_length, next_compose_length);
+  }
+  
+--- 2000,2044 ----
+    }
+    //NSLog(@"setMarkedText: %@ %d %d",received,newSelection.location,newSelection.length);
++ 
++   fl_lock_function();
++ 
++   // Simple keyboard widgets generally do not want these side channel
++   // inputs, but we have no other way of getting dead keys so we make
++   // an exception in that case.
++   if (use_simple_keyboard) {
++     if (in_key_event && (Fl::e_length == 0)) {
++       [FLView prepareEtext:received];
++ 
++       Fl::e_text = (char*)cocoaDead2FLTK(Fl::e_text);
++       Fl::e_length = strlen(Fl::e_text);
++     }
++     goto end;
++   }
++ 
+    // This code creates the OS X behaviour of seeing dead keys as things
+    // are being composed.
++   //
++   // Note: The concatenation thing is because of how OS X deals with
++   //       invalid sequences. At that point it will spit out one call
++   //       to insertText with the now aborted sequence, and one new
++   //       call to setMarkedText with the new sequence. Since we want
++   //       both to be visible, we need to concatenate.
+    next_compose_length = newSelection.location;
+!   current = [NSString stringWithUTF8String:Fl::e_text];
+!   aggregate = [current stringByAppendingString:received];
+! 
+!   [FLView prepareEtext:aggregate];
+!   //NSLog(@"Fl::e_text=%@ Fl::e_length=%d next_compose_length=%d", aggregate, Fl::e_length, next_compose_length);
+! 
+!   // We can get called outside of key events (e.g. from the character
+!   // palette). We need to fake our own key event at that point.
+!   if (!in_key_event) {
+!     Fl_Window *target = [(FLWindow*)[self window] getFl_Window];
+!     Fl::e_keysym = Fl::e_original_keysym = 0;
+!     Fl::handle(FL_KEYDOWN, target);
+!   }
+! 
+! end:
+!   fl_unlock_function();
+  }
+  
+***************
+*** 1982,1985 ****
+--- 2110,2129 ----
+  @end
+  
++ void fullscreen_x(Fl_Window *w) {
++   w->_set_fullscreen();
++   /* On OS X < 10.6, it is necessary to recreate the window. This is done
++      with hide+show. */
++   w->hide();
++   w->show();
++   Fl::handle(FL_FULLSCREEN, w);
++ }
++ 
++ void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H) {
++   w->_clear_fullscreen();
++   w->hide();
++   w->resize(X, Y, W, H);
++   w->show();
++   Fl::handle(FL_FULLSCREEN, w);
++ }
+  
+  /*
+***************
+*** 1997,2001 ****
+      x->region = 0;
+      x->subRegion = 0;
+!     x->cursor = fl_default_cursor;
+      x->gc = 0;			// stay 0 for Quickdraw; fill with CGContext for Quartz
+      Fl_Window *win = w->window();
+--- 2141,2145 ----
+      x->region = 0;
+      x->subRegion = 0;
+!     x->cursor = NULL;
+      x->gc = 0;			// stay 0 for Quickdraw; fill with CGContext for Quartz
+      Fl_Window *win = w->window();
+***************
+*** 2099,2103 ****
+      x->region = 0;
+      x->subRegion = 0;
+!     x->cursor = fl_default_cursor;
+      x->xidChildren = 0;
+      x->xidNext = 0;
+--- 2243,2247 ----
+      x->region = 0;
+      x->subRegion = 0;
+!     x->cursor = NULL;
+      x->xidChildren = 0;
+      x->xidNext = 0;
+***************
+*** 2105,2108 ****
+--- 2249,2259 ----
+  	  
+      NSRect srect = [[NSScreen mainScreen] frame];
++     if (w->flags() & Fl_Widget::FULLSCREEN) {
++       int sx, sy, sw, sh;
++       Fl::screen_xywh(sx, sy, sw, sh, w->x(), w->y(), w->w(), w->h());
++       w->resize(sx, sy, sw, sh);
++       winstyle = NSBorderlessWindowMask;
++       winlevel = NSStatusWindowLevel;
++     }
+      NSRect crect;
+      crect.origin.x = w->x(); 
+***************
+*** 2553,2556 ****
+--- 2704,2728 ----
+  }
+  
++ extern void fl_trigger_clipboard_notify(int source);
++ 
++ void fl_clipboard_notify_change() {
++   // No need to do anything here...
++ }
++ 
++ static void clipboard_check(void)
++ {
++   PasteboardSyncFlags flags;
++ 
++   allocatePasteboard();
++   flags = PasteboardSynchronize(myPasteboard);
++ 
++   if (!(flags & kPasteboardModified))
++     return;
++   if (flags & kPasteboardClientIsOwner)
++     return;
++ 
++   fl_trigger_clipboard_notify(1);
++ }
++ 
+  void Fl::add_timeout(double time, Fl_Timeout_Handler cb, void* data)
+  {
+***************
+*** 2677,2680 ****
+--- 2849,2856 ----
+      [(NSWindow *)xid close];
+    }
++   if (cursor) {
++     [(NSCursor*)cursor release];
++     cursor = NULL;
++   }
+  }
+  
+***************
+*** 2792,2857 ****
+  }
+  
+! static NSCursor *PrepareCursor(NSCursor *cursor, CGContextRef (*f)() )
+  {
+!   if (cursor == nil) {
+!     CGContextRef c = f();
+!     NSImage *image = CGBitmapContextToNSImage(c);
+!     fl_delete_offscreen( (Fl_Offscreen)c ); 
+!     NSPoint pt = {[image size].width/2, [image size].height/2};
+!     cursor = [[NSCursor alloc] initWithImage:image hotSpot:pt];
+    }
+-   return cursor;
+- }
+  
+- void Fl_X::set_cursor(Fl_Cursor c)
+- {
+-   NSCursor *icrsr;
+    switch (c) {
+!     case FL_CURSOR_CROSS:  icrsr = [NSCursor crosshairCursor]; break;
+!     case FL_CURSOR_WAIT:
+!       static NSCursor *watch = nil;
+!       watch = PrepareCursor(watch,  &Fl_X::watch_cursor_image);
+!       icrsr = watch;
+!       break;
+!     case FL_CURSOR_INSERT: icrsr = [NSCursor IBeamCursor]; break;
+!     case FL_CURSOR_N:      icrsr = [NSCursor resizeUpCursor]; break;
+!     case FL_CURSOR_S:      icrsr = [NSCursor resizeDownCursor]; break;
+!     case FL_CURSOR_NS:     icrsr = [NSCursor resizeUpDownCursor]; break;
+!     case FL_CURSOR_HELP:   
+!       static NSCursor *help = nil;
+!       help = PrepareCursor(help,  &Fl_X::help_cursor_image);
+!       icrsr = help;
+!       break;
+!     case FL_CURSOR_HAND:   icrsr = [NSCursor pointingHandCursor]; break;
+!     case FL_CURSOR_MOVE:   icrsr = [NSCursor openHandCursor]; break;
+!     case FL_CURSOR_NE:
+!     case FL_CURSOR_SW:
+!     case FL_CURSOR_NESW:   
+!       static NSCursor *nesw = nil;
+!       nesw = PrepareCursor(nesw,  &Fl_X::nesw_cursor_image);
+!       icrsr = nesw;
+!       break;
+!     case FL_CURSOR_E:      icrsr = [NSCursor resizeRightCursor]; break;
+!     case FL_CURSOR_W:      icrsr = [NSCursor resizeLeftCursor]; break;
+!     case FL_CURSOR_WE:     icrsr = [NSCursor resizeLeftRightCursor]; break;
+!     case FL_CURSOR_SE:
+!     case FL_CURSOR_NW:
+!     case FL_CURSOR_NWSE:   
+!       static NSCursor *nwse = nil;
+!       nwse = PrepareCursor(nwse,  &Fl_X::nwse_cursor_image);
+!       icrsr = nwse;
+!       break;
+!     case FL_CURSOR_NONE:   
+!       static NSCursor *none = nil;
+!       none = PrepareCursor(none,  &Fl_X::none_cursor_image);
+!       icrsr = none; 
+!       break;
+!     case FL_CURSOR_ARROW:
+!     case FL_CURSOR_DEFAULT:
+!     default:			   icrsr = [NSCursor arrowCursor];
+!       break;
+    }
+!   [icrsr set];
+!   cursor = icrsr;
+  }
+  
+--- 2968,3071 ----
+  }
+  
+! int Fl_X::set_cursor(Fl_Cursor c)
+  {
+!   if (cursor) {
+!     [(NSCursor*)cursor release];
+!     cursor = NULL;
+    }
+  
+    switch (c) {
+!   case FL_CURSOR_ARROW:   cursor = [NSCursor arrowCursor]; break;
+!   case FL_CURSOR_CROSS:   cursor = [NSCursor crosshairCursor]; break;
+!   case FL_CURSOR_INSERT:  cursor = [NSCursor IBeamCursor]; break;
+!   case FL_CURSOR_HAND:    cursor = [NSCursor pointingHandCursor]; break;
+!   case FL_CURSOR_MOVE:    cursor = [NSCursor openHandCursor]; break;
+!   case FL_CURSOR_NS:      cursor = [NSCursor resizeUpDownCursor]; break;
+!   case FL_CURSOR_WE:      cursor = [NSCursor resizeLeftRightCursor]; break;
+!   case FL_CURSOR_N:       cursor = [NSCursor resizeUpCursor]; break;
+!   case FL_CURSOR_E:       cursor = [NSCursor resizeRightCursor]; break;
+!   case FL_CURSOR_W:       cursor = [NSCursor resizeLeftCursor]; break;
+!   case FL_CURSOR_S:       cursor = [NSCursor resizeDownCursor]; break;
+!   default:
+!     return 0;
+!   }
+! 
+!   [(NSCursor*)cursor retain];
+! 
+!   [(NSWindow*)xid invalidateCursorRectsForView:[(NSWindow*)xid contentView]];
+! 
+!   return 1;
+! }
+! 
+! int Fl_X::set_cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
+!   if (cursor) {
+!     [(NSCursor*)cursor release];
+!     cursor = NULL;
+!   }
+! 
+!   if ((hotx < 0) || (hotx >= image->w()))
+!     return 0;
+!   if ((hoty < 0) || (hoty >= image->h()))
+!     return 0;
+! 
+!   // OS X >= 10.6 can create a NSImage from a CGImage, but we need to
+!   // support older versions, hence this pesky handling.
+! 
+!   NSBitmapImageRep *bitmap = [[NSBitmapImageRep alloc]
+!                               initWithBitmapDataPlanes:NULL
+!                               pixelsWide:image->w()
+!                               pixelsHigh:image->h()
+!                               bitsPerSample:8
+!                               samplesPerPixel:image->d()
+!                               hasAlpha:!(image->d() & 1)
+!                               isPlanar:NO
+!                               colorSpaceName:(image->d()<=2) ? NSDeviceWhiteColorSpace : NSDeviceRGBColorSpace
+!                               bytesPerRow:(image->w() * image->d())
+!                               bitsPerPixel:(image->d()*8)];
+! 
+!   // Alpha needs to be premultiplied for this format
+! 
+!   const uchar *i = (const uchar*)*image->data();
+!   unsigned char *o = [bitmap bitmapData];
+!   for (int y = 0;y < image->h();y++) {
+!     if (image->d() & 1) {
+!       for (int x = 0;x < image->w();x++) {
+!         unsigned int alpha;
+!         if (image->d() == 4) {
+!           alpha = i[3];
+!           *o++ = (unsigned char)((unsigned int)*i++ * alpha / 255);
+!           *o++ = (unsigned char)((unsigned int)*i++ * alpha / 255);
+!         }
+! 
+!         alpha = i[1];
+!         *o++ = (unsigned char)((unsigned int)*i++ * alpha / 255);
+!         *o++ = alpha;
+!         i++;
+!       }
+!     } else {
+!       // No alpha, so we can just copy everything directly.
+!       int len = image->w() * image->d();
+!       memcpy(o, i, len);
+!       o += len;
+!       i += len;
+!     }
+!     i += image->ld();
+    }
+! 
+!   NSImage *nsimage = [[NSImage alloc]
+!                       initWithSize:NSMakeSize(image->w(), image->h())];
+! 
+!   [nsimage addRepresentation:bitmap];
+! 
+!   cursor = [[NSCursor alloc]
+!             initWithImage:nsimage
+!             hotSpot:NSMakePoint(hotx, hoty)];
+! 
+!   [(NSWindow*)xid invalidateCursorRectsForView:[(NSWindow*)xid contentView]];
+! 
+!   [bitmap release];
+!   [nsimage release];
+! 
+!   return 1;
+  }
+  
+*** fltk-1.3.0/src/Fl_grab.cxx	2010-12-18 16:31:01.000000000 -0600
+--- fltk-1.3.0.new/src/Fl_grab.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 39,42 ****
+--- 39,43 ----
+  
+  extern void fl_fix_focus(); // in Fl.cxx
++ void fl_update_focus(void);
+  
+  #ifdef WIN32
+***************
+*** 51,55 ****
+--- 52,68 ----
+  #endif
+  
++ #if !(defined(WIN32) || defined(__APPLE__))
++ extern int ewmh_supported(); // from Fl_x.cxx
++ #endif
++ 
+  void Fl::grab(Fl_Window* win) {
++     Fl_Window *fullscreen_win = NULL;
++     for (Fl_Window *W = Fl::first_window(); W; W = Fl::next_window(W)) {
++       if (W->fullscreen_active()) {
++         fullscreen_win = W;
++         break;
++       }
++     }
++ 
+    if (win) {
+      if (!grab_) {
+***************
+*** 61,66 ****
+        Fl_X::i(first_window())->set_key_window();
+  #else
+        XGrabPointer(fl_display,
+! 		   fl_xid(first_window()),
+  		   1,
+  		   ButtonPressMask|ButtonReleaseMask|
+--- 74,80 ----
+        Fl_X::i(first_window())->set_key_window();
+  #else
++       Window xid = fullscreen_win ? fl_xid(fullscreen_win) : fl_xid(first_window());
+        XGrabPointer(fl_display,
+! 		   xid,
+  		   1,
+  		   ButtonPressMask|ButtonReleaseMask|
+***************
+*** 72,76 ****
+  		   fl_event_time);
+        XGrabKeyboard(fl_display,
+! 		    fl_xid(first_window()),
+  		    1,
+  		    GrabModeAsync,
+--- 86,90 ----
+  		   fl_event_time);
+        XGrabKeyboard(fl_display,
+! 		    xid,
+  		    1,
+  		    GrabModeAsync,
+***************
+*** 80,83 ****
+--- 94,98 ----
+      }
+      grab_ = win;
++     fl_update_focus();
+    } else {
+      if (grab_) {
+***************
+*** 88,92 ****
+--- 103,110 ----
+        fl_capture = 0;
+  #else
++       // We must keep the grab in the non-EWMH fullscreen case
++       if (!fullscreen_win || ewmh_supported()) {
+        XUngrabKeyboard(fl_display, fl_event_time);
++       }
+        XUngrabPointer(fl_display, fl_event_time);
+        // this flush is done in case the picked menu item goes into
+***************
+*** 95,98 ****
+--- 113,117 ----
+  #endif
+        grab_ = 0;
++       fl_update_focus();
+        fl_fix_focus();
+      }
+*** fltk-1.3.0/src/Fl_win32.cxx	2011-05-30 07:33:51.000000000 -0500
+--- fltk-1.3.0.new/src/Fl_win32.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 99,102 ****
+--- 99,104 ----
+  Fl_Display_Device *Fl_Display_Device::_display = &fl_gdi_display; // the platform display
+  
++ bool use_simple_keyboard = false;
++ 
+  // dynamic wsock dll handling api:
+  #if defined(__CYGWIN__) && !defined(SOCKET)
+***************
+*** 132,135 ****
+--- 134,139 ----
    */
--  void cursor(Fl_Cursor, Fl_Color=FL_BLACK, Fl_Color=FL_WHITE); // platform dependent
--  void default_cursor(Fl_Cursor, Fl_Color=FL_BLACK, Fl_Color=FL_WHITE);
-+  void cursor(Fl_Cursor);
-+  void cursor(const Fl_RGB_Image*, int, int);
-+  void default_cursor(Fl_Cursor);
-+
-+  /* for legacy compatibility */
-+  void cursor(Fl_Cursor c, Fl_Color, Fl_Color=FL_WHITE) { cursor(c); };
-+  void default_cursor(Fl_Cursor c, Fl_Color, Fl_Color=FL_WHITE) { default_cursor(c); };
-+
-   static void default_callback(Fl_Window*, void* v);
-   
-   /** Returns the window width including any frame added by the window manager.
-diff -up fltk-1.3.x-r8772/FL/mac.H.cursor fltk-1.3.x-r8772/FL/mac.H
---- fltk-1.3.x-r8772/FL/mac.H.cursor	2011-05-12 13:50:43.000000000 +0200
-+++ fltk-1.3.x-r8772/FL/mac.H	2011-06-08 18:23:14.330145367 +0200
-@@ -141,7 +141,8 @@ public:
-   void collapse(void);
-   WindowRef window_ref(void);
-   void set_key_window(void);
--  void set_cursor(Fl_Cursor);
-+  int set_cursor(Fl_Cursor);
-+  int set_cursor(const Fl_RGB_Image*, int, int);
-   static CGImageRef CGImage_from_window_rect(Fl_Window *win, int x, int y, int w, int h);
-   static unsigned char *bitmap_from_window_rect(Fl_Window *win, int x, int y, int w, int h, int *bytesPerPixel);
-   static Fl_Region intersect_region_and_rect(Fl_Region current, int x,int y,int w, int h);
-diff -up fltk-1.3.x-r8772/FL/win32.H.cursor fltk-1.3.x-r8772/FL/win32.H
---- fltk-1.3.x-r8772/FL/win32.H.cursor	2011-05-23 20:32:47.000000000 +0200
-+++ fltk-1.3.x-r8772/FL/win32.H	2011-06-08 18:23:14.331145463 +0200
-@@ -92,6 +92,8 @@ public:
-   void flush() {w->flush();}
-   void set_minmax(LPMINMAXINFO minmax);
-   void mapraise();
-+  int set_cursor(Fl_Cursor);
-+  int set_cursor(const Fl_RGB_Image*, int, int);
-   static Fl_X* make(Fl_Window*);
- };
- extern FL_EXPORT HCURSOR fl_default_cursor;
-diff -up fltk-1.3.x-r8772/FL/x.H.cursor fltk-1.3.x-r8772/FL/x.H
---- fltk-1.3.x-r8772/FL/x.H.cursor	2011-05-21 12:05:19.000000000 +0200
-+++ fltk-1.3.x-r8772/FL/x.H	2011-06-08 18:23:14.331145463 +0200
-@@ -163,6 +163,8 @@ public:
-   static Fl_X* i(const Fl_Window* wi) {return wi->i;}
-   void setwindow(Fl_Window* wi) {w=wi; wi->i=this;}
-   void sendxjunk();
-+  int set_cursor(Fl_Cursor);
-+  int set_cursor(const Fl_RGB_Image*, int, int);
-   static void make_xid(Fl_Window*,XVisualInfo* =fl_visual, Colormap=fl_colormap);
-   static Fl_X* set_xid(Fl_Window*, Window);
-   // kludges to get around protection:
-diff -up fltk-1.3.x-r8772/src/Fl_cocoa.mm.cursor fltk-1.3.x-r8772/src/Fl_cocoa.mm
---- fltk-1.3.x-r8772/src/Fl_cocoa.mm.cursor	2011-06-08 18:23:14.290141618 +0200
-+++ fltk-1.3.x-r8772/src/Fl_cocoa.mm	2011-06-08 18:23:14.334145743 +0200
-@@ -108,7 +108,6 @@ int fl_screen;
- CGContextRef fl_gc = 0;
- void *fl_system_menu;                   // this is really a NSMenu*
- Fl_Sys_Menu_Bar *fl_sys_menu_bar = 0;
--void *fl_default_cursor;		// this is really a NSCursor*
- void *fl_capture = 0;			// (NSWindow*) we need this to compensate for a missing(?) mouse capture
- bool fl_show_iconic;                    // true if called from iconize() - shows the next created window in collapsed state
- //int fl_disable_transient_for;           // secret method of removing TRANSIENT_FOR
-@@ -1355,8 +1354,6 @@ void fl_open_display() {
- 					  dequeue:YES];
-     while (ign_event);
-     
--    fl_default_cursor = [NSCursor arrowCursor];
--
-     // bring the application into foreground without a 'CARB' resource
-     Boolean same_psn;
-     ProcessSerialNumber cur_psn, front_psn;
-@@ -1656,6 +1653,7 @@ static void  q_set_window_title(NSWindow
- - (void)drawRect:(NSRect)rect;
- - (BOOL)acceptsFirstResponder;
- - (BOOL)acceptsFirstMouse:(NSEvent*)theEvent;
-+- (void)resetCursorRects;
- - (BOOL)performKeyEquivalent:(NSEvent*)theEvent;
- - (void)mouseUp:(NSEvent *)theEvent;
- - (void)rightMouseUp:(NSEvent *)theEvent;
-@@ -1713,6 +1711,16 @@ static void  q_set_window_title(NSWindow
-   Fl_Window *first = Fl::first_window();
-   return (first == w || !first->modal());
- }
-+- (void)resetCursorRects {
-+  Fl_Window *w = [(FLWindow*)[self window] getFl_Window];
-+  Fl_X *i = Fl_X::i(w);
-+  // We have to have at least one cursor rect for invalidateCursorRectsForView
-+  // to work, hence the "else" clause.
-+  if (i->cursor)
-+    [self addCursorRect:[self visibleRect] cursor:(NSCursor*)i->cursor];
-+  else
-+    [self addCursorRect:[self visibleRect] cursor:[NSCursor arrowCursor]];
-+}
- - (void)mouseUp:(NSEvent *)theEvent {
-   cocoaMouseHandler(theEvent);
- }
-@@ -2130,7 +2138,7 @@ void Fl_X::make(Fl_Window* w)
-     x->other_xid = 0;
-     x->region = 0;
-     x->subRegion = 0;
--    x->cursor = fl_default_cursor;
-+    x->cursor = NULL;
-     x->gc = 0;			// stay 0 for Quickdraw; fill with CGContext for Quartz
-     Fl_Window *win = w->window();
-     Fl_X *xo = Fl_X::i(win);
-@@ -2232,7 +2240,7 @@ void Fl_X::make(Fl_Window* w)
-     x->other_xid = 0; // room for doublebuffering image map. On OS X this is only used by overlay windows
-     x->region = 0;
-     x->subRegion = 0;
--    x->cursor = fl_default_cursor;
-+    x->cursor = NULL;
-     x->xidChildren = 0;
-     x->xidNext = 0;
-     x->gc = 0;
-@@ -2838,6 +2846,10 @@ void Fl_X::destroy() {
-     [[(NSWindow *)xid contentView] release];
-     [(NSWindow *)xid close];
-   }
-+  if (cursor) {
-+    [(NSCursor*)cursor release];
-+    cursor = NULL;
-+  }
- }
- 
- void Fl_X::map() {
-@@ -2953,68 +2965,106 @@ static NSImage *CGBitmapContextToNSImage
-   return [image autorelease];
- }
- 
--static NSCursor *PrepareCursor(NSCursor *cursor, CGContextRef (*f)() )
-+int Fl_X::set_cursor(Fl_Cursor c)
- {
--  if (cursor == nil) {
--    CGContextRef c = f();
--    NSImage *image = CGBitmapContextToNSImage(c);
--    fl_delete_offscreen( (Fl_Offscreen)c ); 
--    NSPoint pt = {[image size].width/2, [image size].height/2};
--    cursor = [[NSCursor alloc] initWithImage:image hotSpot:pt];
-+  if (cursor) {
-+    [(NSCursor*)cursor release];
-+    cursor = NULL;
-   }
--  return cursor;
--}
- 
--void Fl_X::set_cursor(Fl_Cursor c)
--{
--  NSCursor *icrsr;
-   switch (c) {
--    case FL_CURSOR_CROSS:  icrsr = [NSCursor crosshairCursor]; break;
--    case FL_CURSOR_WAIT:
--      static NSCursor *watch = nil;
--      watch = PrepareCursor(watch,  &Fl_X::watch_cursor_image);
--      icrsr = watch;
--      break;
--    case FL_CURSOR_INSERT: icrsr = [NSCursor IBeamCursor]; break;
--    case FL_CURSOR_N:      icrsr = [NSCursor resizeUpCursor]; break;
--    case FL_CURSOR_S:      icrsr = [NSCursor resizeDownCursor]; break;
--    case FL_CURSOR_NS:     icrsr = [NSCursor resizeUpDownCursor]; break;
--    case FL_CURSOR_HELP:   
--      static NSCursor *help = nil;
--      help = PrepareCursor(help,  &Fl_X::help_cursor_image);
--      icrsr = help;
--      break;
--    case FL_CURSOR_HAND:   icrsr = [NSCursor pointingHandCursor]; break;
--    case FL_CURSOR_MOVE:   icrsr = [NSCursor openHandCursor]; break;
--    case FL_CURSOR_NE:
--    case FL_CURSOR_SW:
--    case FL_CURSOR_NESW:   
--      static NSCursor *nesw = nil;
--      nesw = PrepareCursor(nesw,  &Fl_X::nesw_cursor_image);
--      icrsr = nesw;
--      break;
--    case FL_CURSOR_E:      icrsr = [NSCursor resizeRightCursor]; break;
--    case FL_CURSOR_W:      icrsr = [NSCursor resizeLeftCursor]; break;
--    case FL_CURSOR_WE:     icrsr = [NSCursor resizeLeftRightCursor]; break;
--    case FL_CURSOR_SE:
--    case FL_CURSOR_NW:
--    case FL_CURSOR_NWSE:   
--      static NSCursor *nwse = nil;
--      nwse = PrepareCursor(nwse,  &Fl_X::nwse_cursor_image);
--      icrsr = nwse;
--      break;
--    case FL_CURSOR_NONE:   
--      static NSCursor *none = nil;
--      none = PrepareCursor(none,  &Fl_X::none_cursor_image);
--      icrsr = none; 
--      break;
--    case FL_CURSOR_ARROW:
--    case FL_CURSOR_DEFAULT:
--    default:			   icrsr = [NSCursor arrowCursor];
--      break;
-+  case FL_CURSOR_ARROW:   cursor = [NSCursor arrowCursor]; break;
-+  case FL_CURSOR_CROSS:   cursor = [NSCursor crosshairCursor]; break;
-+  case FL_CURSOR_INSERT:  cursor = [NSCursor IBeamCursor]; break;
-+  case FL_CURSOR_HAND:    cursor = [NSCursor pointingHandCursor]; break;
-+  case FL_CURSOR_MOVE:    cursor = [NSCursor openHandCursor]; break;
-+  case FL_CURSOR_NS:      cursor = [NSCursor resizeUpDownCursor]; break;
-+  case FL_CURSOR_WE:      cursor = [NSCursor resizeLeftRightCursor]; break;
-+  case FL_CURSOR_N:       cursor = [NSCursor resizeUpCursor]; break;
-+  case FL_CURSOR_E:       cursor = [NSCursor resizeRightCursor]; break;
-+  case FL_CURSOR_W:       cursor = [NSCursor resizeLeftCursor]; break;
-+  case FL_CURSOR_S:       cursor = [NSCursor resizeDownCursor]; break;
-+  default:
-+    return 0;
-+  }
-+
-+  [(NSCursor*)cursor retain];
-+
-+  [(NSWindow*)xid invalidateCursorRectsForView:[(NSWindow*)xid contentView]];
-+
-+  return 1;
-+}
-+
-+int Fl_X::set_cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
-+  if (cursor) {
-+    [(NSCursor*)cursor release];
-+    cursor = NULL;
-+  }
-+
-+  if ((hotx < 0) || (hotx >= image->w()))
-+    return 0;
-+  if ((hoty < 0) || (hoty >= image->h()))
-+    return 0;
-+
-+  // OS X >= 10.6 can create a NSImage from a CGImage, but we need to
-+  // support older versions, hence this pesky handling.
-+
-+  NSBitmapImageRep *bitmap = [[NSBitmapImageRep alloc]
-+                              initWithBitmapDataPlanes:NULL
-+                              pixelsWide:image->w()
-+                              pixelsHigh:image->h()
-+                              bitsPerSample:8
-+                              samplesPerPixel:image->d()
-+                              hasAlpha:!(image->d() & 1)
-+                              isPlanar:NO
-+                              colorSpaceName:(image->d()<=2) ? NSDeviceWhiteColorSpace : NSDeviceRGBColorSpace
-+                              bytesPerRow:(image->w() * image->d())
-+                              bitsPerPixel:(image->d()*8)];
-+
-+  // Alpha needs to be premultiplied for this format
-+
-+  const uchar *i = (const uchar*)*image->data();
-+  unsigned char *o = [bitmap bitmapData];
-+  for (int y = 0;y < image->h();y++) {
-+    if (image->d() & 1) {
-+      for (int x = 0;x < image->w();x++) {
-+        unsigned int alpha;
-+        if (image->d() == 4) {
-+          alpha = i[3];
-+          *o++ = (unsigned char)((unsigned int)*i++ * alpha / 255);
-+          *o++ = (unsigned char)((unsigned int)*i++ * alpha / 255);
-+        }
-+
-+        alpha = i[1];
-+        *o++ = (unsigned char)((unsigned int)*i++ * alpha / 255);
-+        *o++ = alpha;
-+        i++;
-+      }
-+    } else {
-+      // No alpha, so we can just copy everything directly.
-+      int len = image->w() * image->d();
-+      memcpy(o, i, len);
-+      o += len;
-+      i += len;
-+    }
-+    i += image->ld();
-   }
--  [icrsr set];
--  cursor = icrsr;
-+
-+  NSImage *nsimage = [[NSImage alloc]
-+                      initWithSize:NSMakeSize(image->w(), image->h())];
-+
-+  [nsimage addRepresentation:bitmap];
-+
-+  cursor = [[NSCursor alloc]
-+            initWithImage:nsimage
-+            hotSpot:NSMakePoint(hotx, hoty)];
-+
-+  [(NSWindow*)xid invalidateCursorRectsForView:[(NSWindow*)xid contentView]];
-+
-+  [bitmap release];
-+  [nsimage release];
-+
-+  return 1;
- }
- 
- @interface FLaboutItemTarget : NSObject 
-diff -up fltk-1.3.x-r8772/src/fl_cursor.cxx.cursor fltk-1.3.x-r8772/src/fl_cursor.cxx
---- fltk-1.3.x-r8772/src/fl_cursor.cxx.cursor	2010-12-18 23:31:01.000000000 +0100
-+++ fltk-1.3.x-r8772/src/fl_cursor.cxx	2011-06-08 18:23:14.335145836 +0200
-@@ -33,300 +33,155 @@
- 
- #include <FL/Fl.H>
- #include <FL/Fl_Window.H>
-+#include <FL/Fl_Pixmap.H>
-+#include <FL/Fl_RGB_Image.H>
- #include <FL/x.H>
--#if !defined(WIN32) && !defined(__APPLE__)
--#  include <X11/cursorfont.h>
--#endif
- #include <FL/fl_draw.H>
- 
-+#include "fl_cursor_wait.xpm"
-+#include "fl_cursor_help.xpm"
-+#include "fl_cursor_nwse.xpm"
-+#include "fl_cursor_nesw.xpm"
-+#include "fl_cursor_none.xpm"
-+
- /**
-   Sets the cursor for the current window to the specified shape and colors.
-   The cursors are defined in the <FL/Enumerations.H> header file. 
-   */
-+void fl_cursor(Fl_Cursor c) {
-+  if (Fl::first_window()) Fl::first_window()->cursor(c);
-+}
-+
-+/* For back compatibility only. */
- void fl_cursor(Fl_Cursor c, Fl_Color fg, Fl_Color bg) {
--  if (Fl::first_window()) Fl::first_window()->cursor(c,fg,bg);
-+  fl_cursor(c);
- }
-+
-+
- /** 
--    Sets the default window cursor as well as its color.
-+    Sets the default window cursor. This is the cursor that will be used
-+    after the mouse pointer leaves a widget with a custom cursor set.
- 
--    For back compatibility only.
-+    \see cursor(const Fl_RGB_Image*, int, int), default_cursor()
- */
--void Fl_Window::default_cursor(Fl_Cursor c, Fl_Color fg, Fl_Color bg) {
--//  if (c == FL_CURSOR_DEFAULT) c = FL_CURSOR_ARROW;
--
-+void Fl_Window::default_cursor(Fl_Cursor c) {
-   cursor_default = c;
--  cursor_fg      = fg;
--  cursor_bg      = bg;
-+  cursor(c);
-+}
-+
- 
--  cursor(c, fg, bg);
-+void fallback_cursor(Fl_Window *w, Fl_Cursor c) {
-+  const char **xpm;
-+  int hotx, hoty;
-+
-+  // The standard arrow is our final fallback, so something is broken
-+  // if we get called back here with that as an argument.
-+  if (c == FL_CURSOR_ARROW)
-+    return;
-+
-+  switch (c) {
-+  case FL_CURSOR_WAIT:
-+    xpm = (const char**)fl_cursor_wait_xpm;
-+    hotx = 8;
-+    hoty = 15;
-+    break;
-+  case FL_CURSOR_HELP:
-+    xpm = (const char**)fl_cursor_help_xpm;
-+    hotx = 1;
-+    hoty = 3;
-+    break;
-+  case FL_CURSOR_NWSE:
-+    xpm = (const char**)fl_cursor_nwse_xpm;
-+    hotx = 7;
-+    hoty = 7;
-+    break;
-+  case FL_CURSOR_NESW:
-+    xpm = (const char**)fl_cursor_nesw_xpm;
-+    hotx = 7;
-+    hoty = 7;
-+    break;
-+  case FL_CURSOR_NONE:
-+    xpm = (const char**)fl_cursor_none_xpm;
-+    hotx = 0;
-+    hoty = 0;
-+    break;
-+  default:
-+    w->cursor(FL_CURSOR_ARROW);
-+    return;
-+  }
-+
-+  Fl_Pixmap pxm(xpm);
-+  Fl_RGB_Image image(&pxm);
-+
-+  w->cursor(&image, hotx, hoty);
- }
- 
--#ifdef WIN32
- 
--#  ifndef IDC_HAND
--#    define IDC_HAND	MAKEINTRESOURCE(32649)
--#  endif // !IDC_HAND
-+void Fl_Window::cursor(Fl_Cursor c) {
-+  int ret;
- 
--void Fl_Window::cursor(Fl_Cursor c, Fl_Color c1, Fl_Color c2) {
--  if (!shown()) return;
-   // the cursor must be set for the top level window, not for subwindows
-   Fl_Window *w = window(), *toplevel = this;
--  while (w) { toplevel = w; w = w->window(); }
--  if (toplevel != this) { toplevel->cursor(c, c1, c2); return; }
--  // now set the actual cursor
--  if (c == FL_CURSOR_DEFAULT) {
--    c = cursor_default;
--  }
--  if (c > FL_CURSOR_NESW) {
--    i->cursor = 0;
--  } else if (c == FL_CURSOR_DEFAULT) {
--    i->cursor = fl_default_cursor;
--  } else {
--    LPSTR n;
--    switch (c) {
--    case FL_CURSOR_ARROW:	n = IDC_ARROW; break;
--    case FL_CURSOR_CROSS:	n = IDC_CROSS; break;
--    case FL_CURSOR_WAIT:	n = IDC_WAIT; break;
--    case FL_CURSOR_INSERT:	n = IDC_IBEAM; break;
--    case FL_CURSOR_HELP:	n = IDC_HELP; break;
--    case FL_CURSOR_HAND: {
--          OSVERSIONINFO osvi;
--
--          // Get the OS version: Windows 98 and 2000 have a standard
--	  // hand cursor.
--          memset(&osvi, 0, sizeof(OSVERSIONINFO));
--          osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
--          GetVersionEx(&osvi);
--
--          if (osvi.dwMajorVersion > 4 ||
--  	      (osvi.dwMajorVersion == 4 && osvi.dwMinorVersion > 0 &&
--  	       osvi.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS)) n = IDC_HAND;
--          else n = IDC_UPARROW;
--	} break;
--    case FL_CURSOR_MOVE:	n = IDC_SIZEALL; break;
--    case FL_CURSOR_N:
--    case FL_CURSOR_S:
--    case FL_CURSOR_NS:		n = IDC_SIZENS; break;
--    case FL_CURSOR_NE:
--    case FL_CURSOR_SW:
--    case FL_CURSOR_NESW:	n = IDC_SIZENESW; break;
--    case FL_CURSOR_E:
--    case FL_CURSOR_W:
--    case FL_CURSOR_WE:		n = IDC_SIZEWE; break;
--    case FL_CURSOR_SE:
--    case FL_CURSOR_NW:
--    case FL_CURSOR_NWSE:	n = IDC_SIZENWSE; break;
--    default:			n = IDC_NO; break;
--    }
--    i->cursor = LoadCursor(NULL, n);
-+
-+  while (w) {
-+    toplevel = w;
-+    w = w->window();
-   }
--  SetCursor(i->cursor);
--}
- 
--#elif defined(__APPLE__)
-+  if (toplevel != this) {
-+    toplevel->cursor(c);
-+    return;
-+  }
- 
--#ifdef __BIG_ENDIAN__
--# define E(x) x
--#elif defined __LITTLE_ENDIAN__
--// Don't worry. This will be resolved at compile time
--# define E(x) (x>>8)|((x<<8)&0xff00)
--#else
--# error "Either __LITTLE_ENDIAN__ or __BIG_ENDIAN__ must be defined"
--#endif
--
--extern Fl_Offscreen fl_create_offscreen_with_alpha(int w, int h);
--
--
--CGContextRef Fl_X::help_cursor_image(void)
--{
--  int w = 20, h = 20;
--  Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
--  fl_begin_offscreen(off);
--  CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
--  fl_rectf(0,0,w,h);
--  fl_color(FL_BLACK);
--  fl_font(FL_COURIER_BOLD, 20);
--  fl_draw("?", 1, h-1);
--  fl_end_offscreen();
--  return (CGContextRef)off;
--}
-+  if (c == FL_CURSOR_DEFAULT)
-+    c = cursor_default;
- 
--CGContextRef Fl_X::none_cursor_image(void)
--{
--  int w = 20, h = 20;
--  Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
--  fl_begin_offscreen(off);
--  CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
--  fl_rectf(0,0,w,h);
--  fl_end_offscreen();
--  return (CGContextRef)off;
--}
-+  if (!i)
-+    return;
- 
--CGContextRef Fl_X::watch_cursor_image(void)
--{
--  int w, h, r = 5;
--  w = 2*r+6;
--  h = 4*r;
--  Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
--  fl_begin_offscreen(off);
--  CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
--  fl_rectf(0,0,w,h);
--  CGContextTranslateCTM( (CGContextRef)off, w/2, h/2);
--  fl_color(FL_WHITE);
--  fl_circle(0, 0, r+1);
--  fl_color(FL_BLACK);
--  fl_rectf(int(-r*0.7), int(-r*1.7), int(1.4*r), int(3.4*r));
--  fl_rectf(r-1, -1, 3, 3);
--  fl_color(FL_WHITE);
--  fl_pie(-r, -r, 2*r, 2*r, 0, 360);
--  fl_color(FL_BLACK);
--  fl_circle(0,0,r);
--  fl_xyline(0, 0, int(-r*.7));
--  fl_xyline(0, 0, 0, int(-r*.7));
--  fl_end_offscreen();
--  return (CGContextRef)off;
--}
-+  ret = i->set_cursor(c);
-+  if (ret)
-+    return;
- 
--CGContextRef Fl_X::nesw_cursor_image(void)
--{
--  int c = 7, r = 2*c;
--  int w = r, h = r;
--  Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
--  fl_begin_offscreen(off);
--  CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
--  fl_rectf(0,0,w,h);
--  CGContextTranslateCTM( (CGContextRef)off, 0, h);
--  CGContextScaleCTM( (CGContextRef)off, 1, -1);
--  fl_color(FL_BLACK);
--  fl_polygon(0, 0, c, 0, 0, c);
--  fl_polygon(r, r, r, r-c, r-c, r);
--  fl_line_style(FL_SOLID, 2, 0);
--  fl_line(0,1, r,r+1);
--  fl_line_style(FL_SOLID, 0, 0);
--  fl_end_offscreen();
--  return (CGContextRef)off;
-+  fallback_cursor(this, c);
- }
- 
--CGContextRef Fl_X::nwse_cursor_image(void)
--{
--  int c = 7, r = 2*c;
--  int w = r, h = r;
--  Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
--  fl_begin_offscreen(off);
--  CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
--  fl_rectf(0,0,w,h);
--  CGContextTranslateCTM( (CGContextRef)off, 0, h);
--  CGContextScaleCTM( (CGContextRef)off, 1, -1);
--  fl_color(FL_BLACK);
--  fl_polygon(r-1, 0, r-1, c, r-1-c, 0);
--  fl_polygon(-1, r, c-1, r, -1, r-c);
--  fl_line_style(FL_SOLID, 2, 0);
--  fl_line(r-1,1, -1,r+1);
--  fl_line_style(FL_SOLID, 0, 0);
--  fl_end_offscreen();
--  return (CGContextRef)off;
--}
-+/**
-+  Changes the cursor for this window.  This always calls the system, if
-+  you are changing the cursor a lot you may want to keep track of how
-+  you set it in a static variable and call this only if the new cursor
-+  is different.
- 
--void Fl_Window::cursor(Fl_Cursor c, Fl_Color, Fl_Color) {
--  if (c == FL_CURSOR_DEFAULT) {
--    c = cursor_default;
--  }
--  if (i) i->set_cursor(c);
--}
-+  The default cursor will be used if the provided image cannot be used
-+  as a cursor.
- 
--#else
-+  \see cursor(Fl_Cursor), default_cursor()
-+*/
-+void Fl_Window::cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
-+  int ret;
- 
--// I like the MSWindows resize cursors, so I duplicate them here:
-+  // the cursor must be set for the top level window, not for subwindows
-+  Fl_Window *w = window(), *toplevel = this;
- 
--#define CURSORSIZE 16
--#define HOTXY 7
--static struct TableEntry {
--  uchar bits[CURSORSIZE*CURSORSIZE/8];
--  uchar mask[CURSORSIZE*CURSORSIZE/8];
--  Cursor cursor;
--} table[] = {
--  {{	// FL_CURSOR_NS
--   0x00, 0x00, 0x80, 0x01, 0xc0, 0x03, 0xe0, 0x07, 0x80, 0x01, 0x80, 0x01,
--   0x80, 0x01, 0x80, 0x01, 0x80, 0x01, 0x80, 0x01, 0x80, 0x01, 0x80, 0x01,
--   0xe0, 0x07, 0xc0, 0x03, 0x80, 0x01, 0x00, 0x00},
--   {
--   0x80, 0x01, 0xc0, 0x03, 0xe0, 0x07, 0xf0, 0x0f, 0xf0, 0x0f, 0xc0, 0x03,
--   0xc0, 0x03, 0xc0, 0x03, 0xc0, 0x03, 0xc0, 0x03, 0xc0, 0x03, 0xf0, 0x0f,
--   0xf0, 0x0f, 0xe0, 0x07, 0xc0, 0x03, 0x80, 0x01}},
--  {{	// FL_CURSOR_EW
--   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x10,
--   0x0c, 0x30, 0xfe, 0x7f, 0xfe, 0x7f, 0x0c, 0x30, 0x08, 0x10, 0x00, 0x00,
--   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
--   {
--   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x1c, 0x38,
--   0xfe, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x7f, 0x1c, 0x38, 0x18, 0x18,
--   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}},
--  {{	// FL_CURSOR_NWSE
--   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x78, 0x00, 0x38, 0x00, 0x78, 0x00,
--   0xe8, 0x00, 0xc0, 0x01, 0x80, 0x03, 0x00, 0x17, 0x00, 0x1e, 0x00, 0x1c,
--   0x00, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
--   {
--   0x00, 0x00, 0x00, 0x00, 0xfc, 0x00, 0xfc, 0x00, 0x7c, 0x00, 0xfc, 0x00,
--   0xfc, 0x01, 0xec, 0x03, 0xc0, 0x37, 0x80, 0x3f, 0x00, 0x3f, 0x00, 0x3e,
--   0x00, 0x3f, 0x00, 0x3f, 0x00, 0x00, 0x00, 0x00}},
--  {{	// FL_CURSOR_NESW
--   0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x1c, 0x00, 0x1e,
--   0x00, 0x17, 0x80, 0x03, 0xc0, 0x01, 0xe8, 0x00, 0x78, 0x00, 0x38, 0x00,
--   0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
--   {
--   0x00, 0x00, 0x00, 0x00, 0x00, 0x3f, 0x00, 0x3f, 0x00, 0x3e, 0x00, 0x3f,
--   0x80, 0x3f, 0xc0, 0x37, 0xec, 0x03, 0xfc, 0x01, 0xfc, 0x00, 0x7c, 0x00,
--   0xfc, 0x00, 0xfc, 0x00, 0x00, 0x00, 0x00, 0x00}},
--  {{0}, {0}} // FL_CURSOR_NONE & unknown
--};
--
--void Fl_Window::cursor(Fl_Cursor c, Fl_Color fg, Fl_Color bg) {
--  if (!shown()) return;
--  Cursor xc;
--  int deleteit = 0;
--  if (c == FL_CURSOR_DEFAULT) {
--    c  = cursor_default;
--    fg = cursor_fg;
--    bg = cursor_bg;
-+  while (w) {
-+    toplevel = w;
-+    w = w->window();
-   }
- 
--  if (!c) {
--    xc = None;
--  } else {
--    if (c >= FL_CURSOR_NS) {
--      TableEntry *q = (c > FL_CURSOR_NESW) ? table+4 : table+(c-FL_CURSOR_NS);
--      if (!(q->cursor)) {
--	XColor dummy = { 0 };
--	Pixmap p = XCreateBitmapFromData(fl_display,
--	  RootWindow(fl_display, fl_screen), (const char*)(q->bits),
--	  CURSORSIZE, CURSORSIZE);
--	Pixmap m = XCreateBitmapFromData(fl_display,
--	  RootWindow(fl_display, fl_screen), (const char*)(q->mask),
--	  CURSORSIZE, CURSORSIZE);
--	q->cursor = XCreatePixmapCursor(fl_display, p,m,&dummy, &dummy,
--					HOTXY, HOTXY);
--	XFreePixmap(fl_display, m);
--	XFreePixmap(fl_display, p);
--      }
--      xc = q->cursor;
--    } else {
--      xc = XCreateFontCursor(fl_display, (c-1)*2);
--      deleteit = 1;
--    }
--    XColor fgc;
--    uchar r,g,b;
--    Fl::get_color(fg,r,g,b);
--    fgc.red = r<<8; fgc.green = g<<8; fgc.blue = b<<8;
--    XColor bgc;
--    Fl::get_color(bg,r,g,b);
--    bgc.red = r<<8; bgc.green = g<<8; bgc.blue = b<<8;
--    XRecolorCursor(fl_display, xc, &fgc, &bgc);
-+  if (toplevel != this) {
-+    toplevel->cursor(image, hotx, hoty);
-+    return;
-   }
--  XDefineCursor(fl_display, fl_xid(this), xc);
--  if (deleteit) XFreeCursor(fl_display, xc);
--}
- 
--#endif
-+  if (!i)
-+    return;
-+
-+  ret = i->set_cursor(image, hotx, hoty);
-+  if (ret)
-+    return;
-+
-+  cursor(FL_CURSOR_DEFAULT);
-+}
- 
- //
- // End of "$Id: fl_cursor.cxx 8055 2010-12-18 22:31:01Z manolo $".
-diff -up fltk-1.3.x-r8772/src/fl_cursor_help.xpm.cursor fltk-1.3.x-r8772/src/fl_cursor_help.xpm
---- fltk-1.3.x-r8772/src/fl_cursor_help.xpm.cursor	2011-06-08 18:23:14.336145931 +0200
-+++ fltk-1.3.x-r8772/src/fl_cursor_help.xpm	2011-06-08 18:23:14.336145931 +0200
-@@ -0,0 +1,95 @@
-+/* XPM */
-+static const char * fl_cursor_help_xpm[] = {
-+"16 27 65 1",
-+" 	c None",
-+".	c #FFFFFF",
-+"+	c #E2E2E2",
-+"@	c #1C1C1C",
-+"#	c #E7E7E7",
-+"$	c #000000",
-+"%	c #212121",
-+"&	c #EAEAEA",
-+"*	c #262626",
-+"=	c #EDEDED",
-+"-	c #2C2C2C",
-+";	c #F0F0F0",
-+">	c #333333",
-+",	c #F1F1F1",
-+"'	c #393939",
-+")	c #F3F3F3",
-+"!	c #404040",
-+"~	c #484848",
-+"{	c #F4F4F4",
-+"]	c #050505",
-+"^	c #202020",
-+"/	c #707070",
-+"(	c #F5F5F5",
-+"_	c #040404",
-+":	c #E1E1E1",
-+"<	c #EEEEEE",
-+"[	c #EFEFEF",
-+"}	c #FEFEFE",
-+"|	c #3D3D3D",
-+"1	c #7E7E7E",
-+"2	c #696969",
-+"3	c #414141",
-+"4	c #131313",
-+"5	c #080808",
-+"6	c #454545",
-+"7	c #F2F2F2",
-+"8	c #878787",
-+"9	c #7D7D7D",
-+"0	c #101010",
-+"a	c #111111",
-+"b	c #FDFDFD",
-+"c	c #8A8A8A",
-+"d	c #E6E6E6",
-+"e	c #7B7B7B",
-+"f	c #4C4C4C",
-+"g	c #5C5C5C",
-+"h	c #9F9F9F",
-+"i	c #F9F9F9",
-+"j	c #F7F7F7",
-+"k	c #B1B1B1",
-+"l	c #2E2E2E",
-+"m	c #767676",
-+"n	c #DCDCDC",
-+"o	c #DEDEDE",
-+"p	c #C7C7C7",
-+"q	c #1B1B1B",
-+"r	c #6B6B6B",
-+"s	c #575757",
-+"t	c #797979",
-+"u	c #020202",
-+"v	c #010101",
-+"w	c #FBFBFB",
-+"x	c #D7D7D7",
-+"y	c #D8D8D8",
-+"z	c #060606",
-+"                ",
-+".               ",
-+".+              ",
-+".@#             ",
-+".$%&            ",
-+".$$*=           ",
-+".$$$-;          ",
-+".$$$$>,         ",
-+".$$$$$')        ",
-+".$$$$$$!)       ",
-+".$$$$$$$~{      ",
-+".$$$$]^^^/(     ",
-+".$$$$_:(<<[}    ",
-+".$$|1$2<        ",
-+".$3,(45[        ",
-+".67 78$9,       ",
-+".7   {0a( ....  ",
-+"b    ,c5[defgh, ",
-+"      )ijk_la$m.",
-+"         no.p$q.",
-+"           .r$s.",
-+"          .t$-= ",
-+"          7uv+  ",
-+"          wxy.  ",
-+"          :$z.  ",
-+"          :$z.  ",
-+"          ....  "};
-diff -up fltk-1.3.x-r8772/src/fl_cursor_nesw.xpm.cursor fltk-1.3.x-r8772/src/fl_cursor_nesw.xpm
---- fltk-1.3.x-r8772/src/fl_cursor_nesw.xpm.cursor	2011-06-08 18:23:14.336145931 +0200
-+++ fltk-1.3.x-r8772/src/fl_cursor_nesw.xpm	2011-06-08 18:23:14.336145931 +0200
-@@ -0,0 +1,46 @@
-+/* XPM */
-+static const char * fl_cursor_nesw_xpm[] = {
-+"15 15 28 1",
-+" 	c None",
-+".	c #FFFFFF",
-+"+	c #767676",
-+"@	c #000000",
-+"#	c #4E4E4E",
-+"$	c #0C0C0C",
-+"%	c #494949",
-+"&	c #4D4D4D",
-+"*	c #1B1B1B",
-+"=	c #515151",
-+"-	c #646464",
-+";	c #363636",
-+">	c #6A6A6A",
-+",	c #545454",
-+"'	c #585858",
-+")	c #242424",
-+"!	c #797979",
-+"~	c #2E2E2E",
-+"{	c #444444",
-+"]	c #3B3B3B",
-+"^	c #0A0A0A",
-+"/	c #595959",
-+"(	c #F7F7F7",
-+"_	c #080808",
-+":	c #6B6B6B",
-+"<	c #FDFDFD",
-+"[	c #FCFCFC",
-+"}	c #FEFEFE",
-+"     ..........",
-+"      .+@@@@@@.",
-+"       .#@@@@@.",
-+"        .$@@@@.",
-+"       .%@@@@@.",
-+".     .&@@@*@@.",
-+"..   .=@@@-.;@.",
-+".>. .,@@@'. .).",
-+".@!.'@@@#.   ..",
-+".@@~@@@{.     .",
-+".@@@@@].       ",
-+".@@@@^.        ",
-+".@@@@@/(       ",
-+".______:(      ",
-+"<[[[[[[[[}     "};
-diff -up fltk-1.3.x-r8772/src/fl_cursor_none.xpm.cursor fltk-1.3.x-r8772/src/fl_cursor_none.xpm
---- fltk-1.3.x-r8772/src/fl_cursor_none.xpm.cursor	2011-06-08 18:23:14.337146025 +0200
-+++ fltk-1.3.x-r8772/src/fl_cursor_none.xpm	2011-06-08 18:23:14.337146025 +0200
-@@ -0,0 +1,19 @@
-+/* XPM */
-+static const char * fl_cursor_none_xpm[] = {
-+"15 15 1 1",
-+" 	c None",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               ",
-+"               "};
-diff -up fltk-1.3.x-r8772/src/fl_cursor_nwse.xpm.cursor fltk-1.3.x-r8772/src/fl_cursor_nwse.xpm
---- fltk-1.3.x-r8772/src/fl_cursor_nwse.xpm.cursor	2011-06-08 18:23:14.337146025 +0200
-+++ fltk-1.3.x-r8772/src/fl_cursor_nwse.xpm	2011-06-08 18:23:14.337146025 +0200
-@@ -0,0 +1,46 @@
-+/* XPM */
-+static const char * fl_cursor_nwse_xpm[] = {
-+"15 15 28 1",
-+" 	c None",
-+".	c #FFFFFF",
-+"+	c #000000",
-+"@	c #767676",
-+"#	c #4E4E4E",
-+"$	c #0C0C0C",
-+"%	c #494949",
-+"&	c #1B1B1B",
-+"*	c #4D4D4D",
-+"=	c #363636",
-+"-	c #646464",
-+";	c #515151",
-+">	c #242424",
-+",	c #585858",
-+"'	c #545454",
-+")	c #6A6A6A",
-+"!	c #797979",
-+"~	c #444444",
-+"{	c #2E2E2E",
-+"]	c #3B3B3B",
-+"^	c #0A0A0A",
-+"/	c #F7F7F7",
-+"(	c #595959",
-+"_	c #6B6B6B",
-+":	c #080808",
-+"<	c #FEFEFE",
-+"[	c #FCFCFC",
-+"}	c #FDFDFD",
-+"..........     ",
-+".++++++@.      ",
-+".+++++#.       ",
-+".++++$.        ",
-+".+++++%.       ",
-+".++&+++*.     .",
-+".+=.-+++;.   ..",
-+".>. .,+++'. .).",
-+"..   .#+++,.!+.",
-+".     .~+++{++.",
-+"       .]+++++.",
-+"        .^++++.",
-+"       /(+++++.",
-+"      /_::::::.",
-+"     <[[[[[[[[}"};
-diff -up fltk-1.3.x-r8772/src/fl_cursor_wait.xpm.cursor fltk-1.3.x-r8772/src/fl_cursor_wait.xpm
---- fltk-1.3.x-r8772/src/fl_cursor_wait.xpm.cursor	2011-06-08 18:23:14.338146118 +0200
-+++ fltk-1.3.x-r8772/src/fl_cursor_wait.xpm	2011-06-08 18:23:14.338146118 +0200
-@@ -0,0 +1,72 @@
-+/* XPM */
-+static const char * fl_cursor_wait_xpm[] = {
-+"17 32 37 1",
-+" 	c None",
-+".	c #FFFFFF",
-+"+	c #2E2E2E",
-+"@	c #202020",
-+"#	c #F1F1F1",
-+"$	c #2D2D2D",
-+"%	c #000000",
-+"&	c #EDEDED",
-+"*	c #585858",
-+"=	c #575757",
-+"-	c #FBFBFB",
-+";	c #848484",
-+">	c #B8B8B8",
-+",	c #E5E5E5",
-+"'	c #F7F7F7",
-+")	c #181818",
-+"!	c #F0F0F0",
-+"~	c #616161",
-+"{	c #B7B7B7",
-+"]	c #F5F5F5",
-+"^	c #050505",
-+"/	c #D4D4D4",
-+"(	c #EEEEEE",
-+"_	c #595959",
-+":	c #7B7B7B",
-+"<	c #E9E9E9",
-+"[	c #131313",
-+"}	c #E3E3E3",
-+"|	c #767676",
-+"1	c #505050",
-+"2	c #F3F3F3",
-+"3	c #2A2A2A",
-+"4	c #070707",
-+"5	c #343434",
-+"6	c #939393",
-+"7	c #191919",
-+"8	c #6A6A6A",
-+".................",
-+".+@@@@@@@@@@@@@+.",
-+".................",
-+" #$%%%%%%%%%%%$# ",
-+" &*%%%%%%%%%%%=& ",
-+" -;%%%%%%%%%%%;- ",
-+"  >%%%%%%%%%%%>  ",
-+"  ,%%%%%%%%%%%,  ",
-+"  ')%%%%%%%%%)'  ",
-+"  !~%%%%%%%%%~!  ",
-+"   {%%%%%%%%%{   ",
-+"   ]^/...../^]   ",
-+"   (_:.....:_(   ",
-+"    <[}...}[<    ",
-+"    !|1...1|!    ",
-+"     2[3.3[2     ",
-+"     2[%.%[2     ",
-+"    !|%%.%%|!    ",
-+"    <4%%.%%4<    ",
-+"   (_%%%.%%%_(   ",
-+"   ]^%%%.%%%^]   ",
-+"   {%%%%.%%%%{   ",
-+"  !~%%%%.%%%%~!  ",
-+"  ')%%%%.%%%%)'  ",
-+"  ,%%56{.{65%%,  ",
-+"  >%*.......*%>  ",
-+" -;7&.......&7;- ",
-+" &*8.........8=& ",
-+" #$%%%%%%%%%%%$# ",
-+".................",
-+".+@@@@@@@@@@@@@+.",
-+"................."};
-diff -up fltk-1.3.x-r8772/src/Fl_win32.cxx.cursor fltk-1.3.x-r8772/src/Fl_win32.cxx
---- fltk-1.3.x-r8772/src/Fl_win32.cxx.cursor	2011-06-08 18:23:14.292141805 +0200
-+++ fltk-1.3.x-r8772/src/Fl_win32.cxx	2011-06-08 18:23:14.339146212 +0200
-@@ -1635,7 +1635,6 @@ void fl_fix_focus(); // in Fl.cxx
- 
- char fl_show_iconic;	// hack for Fl_Window::iconic()
- // int fl_background_pixel = -1; // color to use for background
--HCURSOR fl_default_cursor;
- UINT fl_wake_msg = 0;
- int fl_disable_transient_for; // secret method of removing TRANSIENT_FOR
- 
-@@ -1683,7 +1682,7 @@ Fl_X* Fl_X::make(Fl_Window* w) {
-     if (!w->icon())
-       w->icon((void *)LoadIcon(NULL, IDI_APPLICATION));
-     wcw.hIcon = wcw.hIconSm = (HICON)w->icon();
--    wcw.hCursor = fl_default_cursor = LoadCursor(NULL, IDC_ARROW);
-+    wcw.hCursor = LoadCursor(NULL, IDC_ARROW);
-     //uchar r,g,b; Fl::get_color(FL_GRAY,r,g,b);
-     //wc.hbrBackground = (HBRUSH)CreateSolidBrush(RGB(r,g,b));
-     wcw.hbrBackground = NULL;
-@@ -1775,7 +1774,7 @@ Fl_X* Fl_X::make(Fl_Window* w) {
-   x->setwindow(w);
-   x->region = 0;
-   x->private_dc = 0;
--  x->cursor = fl_default_cursor;
-+  x->cursor = LoadCursor(NULL, IDC_ARROW);
-   if (!fl_codepage) fl_get_codepage();
- 
-   WCHAR *lab = NULL;
-@@ -2026,6 +2025,129 @@ void Fl_Window::label(const char *name,c
- }
- 
- ////////////////////////////////////////////////////////////////
-+
-+#ifndef IDC_HAND
-+#  define IDC_HAND  MAKEINTRESOURCE(32649)
-+#endif // !IDC_HAND
-+
-+int Fl_X::set_cursor(Fl_Cursor c) {
-+  LPSTR n;
-+
-+  if (c == FL_CURSOR_NONE)
-+    cursor = NULL;
-+  else {
-+    switch (c) {
-+    case FL_CURSOR_ARROW:   n = IDC_ARROW; break;
-+    case FL_CURSOR_CROSS:   n = IDC_CROSS; break;
-+    case FL_CURSOR_WAIT:    n = IDC_WAIT; break;
-+    case FL_CURSOR_INSERT:  n = IDC_IBEAM; break;
-+    case FL_CURSOR_HAND:    n = IDC_HAND; break;
-+    case FL_CURSOR_HELP:    n = IDC_HELP; break;
-+    case FL_CURSOR_MOVE:    n = IDC_SIZEALL; break;
-+    case FL_CURSOR_N:
-+    case FL_CURSOR_S:
-+      // FIXME: Should probably have fallbacks for these instead
-+    case FL_CURSOR_NS:      n = IDC_SIZENS; break;
-+    case FL_CURSOR_NE:
-+    case FL_CURSOR_SW:
-+      // FIXME: Dito.
-+    case FL_CURSOR_NESW:    n = IDC_SIZENESW; break;
-+    case FL_CURSOR_E:
-+    case FL_CURSOR_W:
-+      // FIXME: Dito.
-+    case FL_CURSOR_WE:      n = IDC_SIZEWE; break;
-+    case FL_CURSOR_SE:
-+    case FL_CURSOR_NW:
-+      // FIXME: Dito.
-+    case FL_CURSOR_NWSE:    n = IDC_SIZENWSE; break;
-+    default:
-+      return 0;
-+    }
-+
-+    cursor = LoadCursor(NULL, n);
-+    if (cursor == NULL)
-+      return 0;
-+  }
-+
-+  SetCursor(cursor);
-+
-+  return 1;
-+}
-+
-+int Fl_X::set_cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
-+  BITMAPV5HEADER bi;
-+  HBITMAP bitmap, mask;
-+  DWORD *bits;
-+
-+  if ((hotx < 0) || (hotx >= image->w()))
-+    return 0;
-+  if ((hoty < 0) || (hoty >= image->h()))
-+    return 0;
-+
-+  memset(&bi, 0, sizeof(BITMAPV5HEADER));
-+
-+  bi.bV5Size        = sizeof(BITMAPV5HEADER);
-+  bi.bV5Width       = image->w();
-+  bi.bV5Height      = image->h();
-+  bi.bV5Planes      = 1;
-+  bi.bV5BitCount    = 32;
-+  bi.bV5Compression = BI_BITFIELDS;
-+  bi.bV5RedMask     = 0x00FF0000;
-+  bi.bV5GreenMask   = 0x0000FF00;
-+  bi.bV5BlueMask    = 0x000000FF;
-+  bi.bV5AlphaMask   = 0xFF000000;
-+
-+  HDC hdc;
-+
-+  hdc = GetDC(NULL);
-+  bitmap = CreateDIBSection(hdc, (BITMAPINFO*)&bi, DIB_RGB_COLORS, (void**)&bits, NULL, 0);
-+  ReleaseDC(NULL, hdc);
-+
-+  const uchar *i = (const uchar*)*image->data();
-+  for (int y = 0;y < image->h();y++) {
-+    for (int x = 0;x < image->w();x++) {
-+      switch (image->d()) {
-+      case 1:
-+        *bits = (0xff<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
-+        break;
-+      case 2:
-+        *bits = (i[1]<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
-+        break;
-+      case 3:
-+        *bits = (0xff<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
-+        break;
-+      case 4:
-+        *bits = (i[3]<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
-+        break;
-+      }
-+      i += image->d();
-+      bits++;
-+    }
-+    i += image->ld();
-+  }
-+
-+  // A mask bitmap is still needed even though it isn't used
-+  mask = CreateBitmap(image->w(),image->h(),1,1,NULL);
-+
-+  ICONINFO ii;
-+
-+  ii.fIcon    = FALSE;
-+  ii.xHotspot = hotx;
-+  ii.yHotspot = hoty;
-+  ii.hbmMask  = mask;
-+  ii.hbmColor = bitmap;
-+
-+  cursor = CreateIconIndirect(&ii);
-+
-+  DeleteObject(bitmap);
-+  DeleteObject(mask);
-+
-+  SetCursor(cursor);
-+
-+  return 1;
-+}
-+
-+////////////////////////////////////////////////////////////////
- // Implement the virtual functions for the base Fl_Window class:
- 
- // If the box is a filled rectangle, we can make the redisplay *look*
-diff -up fltk-1.3.x-r8772/src/Fl_Window.cxx.cursor fltk-1.3.x-r8772/src/Fl_Window.cxx
---- fltk-1.3.x-r8772/src/Fl_Window.cxx.cursor	2011-06-08 18:23:14.293141899 +0200
-+++ fltk-1.3.x-r8772/src/Fl_Window.cxx	2011-06-08 18:23:14.340146306 +0200
-@@ -69,8 +69,6 @@ void Fl_Window::_Fl_Window() {
- Fl_Window::Fl_Window(int X,int Y,int W, int H, const char *l)
- : Fl_Group(X, Y, W, H, l) {
-   cursor_default = FL_CURSOR_DEFAULT;
--  cursor_fg      = FL_BLACK;
--  cursor_bg      = FL_WHITE;
- 
-   _Fl_Window();
-   set_flag(FORCE_POSITION);
-@@ -80,8 +78,6 @@ Fl_Window::Fl_Window(int W, int H, const
- // fix common user error of a missing end() with current(0):
-   : Fl_Group((Fl_Group::current(0),0), 0, W, H, l) {
-   cursor_default = FL_CURSOR_DEFAULT;
--  cursor_fg      = FL_BLACK;
--  cursor_bg      = FL_WHITE;
- 
-   _Fl_Window();
-   clear_visible();
-diff -up fltk-1.3.x-r8772/src/Fl_x.cxx.cursor fltk-1.3.x-r8772/src/Fl_x.cxx
---- fltk-1.3.x-r8772/src/Fl_x.cxx.cursor	2011-06-08 18:23:14.296142181 +0200
-+++ fltk-1.3.x-r8772/src/Fl_x.cxx	2011-06-08 18:27:42.302267800 +0200
-@@ -52,6 +52,11 @@
- #  include <X11/Xlocale.h>
- #  include <X11/Xlib.h>
- #  include <X11/keysym.h>
-+#  include <X11/cursorfont.h>
-+
-+#  if HAVE_XCURSOR
-+#    include <X11/Xcursor/Xcursor.h>
-+#  endif
- 
- #  ifdef HAVE_XFIXES
- #  include <X11/extensions/Xfixes.h>
-@@ -2215,6 +2220,94 @@ void Fl_Window::size_range_() {
- 
- ////////////////////////////////////////////////////////////////
- 
-+int Fl_X::set_cursor(Fl_Cursor c) {
-+  unsigned int shape;
-+  Cursor xc;
-+
-+  switch (c) {
-+  case FL_CURSOR_ARROW:   shape = XC_left_ptr; break;
-+  case FL_CURSOR_CROSS:   shape = XC_tcross; break;
-+  case FL_CURSOR_WAIT:    shape = XC_watch; break;
-+  case FL_CURSOR_INSERT:  shape = XC_xterm; break;
-+  case FL_CURSOR_HAND:    shape = XC_hand2; break;
-+  case FL_CURSOR_HELP:    shape = XC_question_arrow; break;
-+  case FL_CURSOR_MOVE:    shape = XC_fleur; break;
-+  case FL_CURSOR_NS:      shape = XC_sb_v_double_arrow; break;
-+  case FL_CURSOR_WE:      shape = XC_sb_h_double_arrow; break;
-+  case FL_CURSOR_NE:      shape = XC_top_right_corner; break;
-+  case FL_CURSOR_N:       shape = XC_top_side; break;
-+  case FL_CURSOR_NW:      shape = XC_top_left_corner; break;
-+  case FL_CURSOR_E:       shape = XC_right_side; break;
-+  case FL_CURSOR_W:       shape = XC_left_side; break;
-+  case FL_CURSOR_SE:      shape = XC_bottom_right_corner; break;
-+  case FL_CURSOR_S:       shape = XC_bottom_side; break;
-+  case FL_CURSOR_SW:      shape = XC_bottom_left_corner; break;
-+  default:
-+    return 0;
-+  }
-+
-+  xc = XCreateFontCursor(fl_display, shape);
-+  XDefineCursor(fl_display, xid, xc);
-+  XFreeCursor(fl_display, xc);
-+
-+  return 1;
-+}
-+
-+int Fl_X::set_cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
-+#if ! HAVE_XCURSOR
-+  return 0;
-+#else
-+  XcursorImage *cursor;
-+  Cursor xc;
-+
-+  if ((hotx < 0) || (hotx >= image->w()))
-+    return 0;
-+  if ((hoty < 0) || (hoty >= image->h()))
-+    return 0;
-+
-+  cursor = XcursorImageCreate(image->w(), image->h());
-+  if (!cursor)
-+    return 0;
-+
-+  const uchar *i = (const uchar*)*image->data();
-+  XcursorPixel *o = cursor->pixels;
-+  for (int y = 0;y < image->h();y++) {
-+    for (int x = 0;x < image->w();x++) {
-+      switch (image->d()) {
-+      case 1:
-+        *o = (0xff<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
-+        break;
-+      case 2:
-+        *o = (i[1]<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
-+        break;
-+      case 3:
-+        *o = (0xff<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
-+        break;
-+      case 4:
-+        *o = (i[3]<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
-+        break;
-+      }
-+      i += image->d();
-+      o++;
-+    }
-+    i += image->ld();
-+  }
-+
-+  cursor->xhot = hotx;
-+  cursor->yhot = hoty;
-+
-+  xc = XcursorImageLoadCursor(fl_display, cursor);
-+  XDefineCursor(fl_display, xid, xc);
-+  XFreeCursor(fl_display, xc);
-+
-+  XcursorImageDestroy(cursor);
-+
-+  return 1;
-+#endif
-+}
-+
-+////////////////////////////////////////////////////////////////
-+
- // returns pointer to the filename, or null if name ends with '/'
- const char *fl_filename_name(const char *name) {
-   const char *p,*q;
-diff -up fltk-1.3.x-r8772/test/cursor.cxx.cursor fltk-1.3.x-r8772/test/cursor.cxx
---- fltk-1.3.x-r8772/test/cursor.cxx.cursor	2010-12-08 15:00:35.000000000 +0100
-+++ fltk-1.3.x-r8772/test/cursor.cxx	2011-06-08 18:23:14.343146587 +0200
-@@ -32,8 +32,6 @@
- #include <FL/fl_draw.H>
- #include <FL/Fl_Box.H>
- 
--Fl_Color fg = FL_BLACK;
--Fl_Color bg = FL_WHITE;
- Fl_Cursor cursor = FL_CURSOR_DEFAULT;
- 
- Fl_Hor_Value_Slider *cursor_slider;
-@@ -41,7 +39,7 @@ Fl_Hor_Value_Slider *cursor_slider;
- void choice_cb(Fl_Widget *, void *v) {
-   cursor = (Fl_Cursor)(fl_intptr_t)v;
-   cursor_slider->value(cursor);
--  fl_cursor(cursor,fg,bg);
-+  fl_cursor(cursor);
- }
- 
- Fl_Menu_Item choices[] = {
-@@ -57,8 +55,6 @@ Fl_Menu_Item choices[] = {
-   {"FL_CURSOR_WE",0,choice_cb,(void*)FL_CURSOR_WE},
-   {"FL_CURSOR_NWSE",0,choice_cb,(void*)FL_CURSOR_NWSE},
-   {"FL_CURSOR_NESW",0,choice_cb,(void*)FL_CURSOR_NESW},
--  {"FL_CURSOR_NONE",0,choice_cb,(void*)FL_CURSOR_NONE},
--#if 0
-   {"FL_CURSOR_N",0,choice_cb,(void*)FL_CURSOR_N},
-   {"FL_CURSOR_NE",0,choice_cb,(void*)FL_CURSOR_NE},
-   {"FL_CURSOR_E",0,choice_cb,(void*)FL_CURSOR_E},
-@@ -67,26 +63,14 @@ Fl_Menu_Item choices[] = {
-   {"FL_CURSOR_SW",0,choice_cb,(void*)FL_CURSOR_SW},
-   {"FL_CURSOR_W",0,choice_cb,(void*)FL_CURSOR_W},
-   {"FL_CURSOR_NW",0,choice_cb,(void*)FL_CURSOR_NW},
--#endif
-+  {"FL_CURSOR_NONE",0,choice_cb,(void*)FL_CURSOR_NONE},
-   {0}
- };
- 
- void setcursor(Fl_Widget *o, void *) {
-   Fl_Hor_Value_Slider *slider = (Fl_Hor_Value_Slider *)o;
-   cursor = Fl_Cursor((int)slider->value());
--  fl_cursor(cursor,fg,bg);
--}
--
--void setfg(Fl_Widget *o, void *) {
--  Fl_Hor_Value_Slider *slider = (Fl_Hor_Value_Slider *)o;
--  fg = Fl_Color((int)slider->value());
--  fl_cursor(cursor,fg,bg);
--}
--
--void setbg(Fl_Widget *o, void *) {
--  Fl_Hor_Value_Slider *slider = (Fl_Hor_Value_Slider *)o;
--  bg = Fl_Color((int)slider->value());
--  fl_cursor(cursor,fg,bg);
-+  fl_cursor(cursor);
- }
- 
- // draw the label without any ^C or \nnn conversions:
-@@ -112,29 +96,11 @@ int main(int argc, char **argv) {
-   slider1.align(FL_ALIGN_LEFT);
-   slider1.step(1);
-   slider1.precision(0);
--  slider1.bounds(0,100);
-+  slider1.bounds(0,255);
-   slider1.value(0);
-   slider1.callback(setcursor);
-   slider1.value(cursor);
- 
--  Fl_Hor_Value_Slider slider2(80,220,310,30,"fgcolor:");
--  slider2.align(FL_ALIGN_LEFT);
--  slider2.step(1);
--  slider2.precision(0);
--  slider2.bounds(0,255);
--  slider2.value(0);
--  slider2.callback(setfg);
--  slider2.value(fg);
--
--  Fl_Hor_Value_Slider slider3(80,260,310,30,"bgcolor:");
--  slider3.align(FL_ALIGN_LEFT);
--  slider3.step(1);
--  slider3.precision(0);
--  slider3.bounds(0,255);
--  slider3.value(0);
--  slider3.callback(setbg);
--  slider3.value(bg);
--
- #if 0
-   // draw the manual's diagram of cursors...
-   window.size(400,800);
+  static HMODULE s_imm_module = 0;
++ typedef BOOL (WINAPI* flTypeImmAssociateContextEx)(HWND, HIMC, DWORD);
++ static flTypeImmAssociateContextEx flImmAssociateContextEx = 0;
+  typedef HIMC (WINAPI* flTypeImmGetContext)(HWND);
+  static flTypeImmGetContext flImmGetContext = 0;
+***************
+*** 147,150 ****
+--- 151,155 ----
+        Fl::fatal("FLTK Lib Error: IMM32.DLL file not found!\n\n"
+          "Please check your input method manager library accessibility.");
++     flImmAssociateContextEx = (flTypeImmAssociateContextEx)GetProcAddress(s_imm_module, "ImmAssociateContextEx");
+      flImmGetContext = (flTypeImmGetContext)GetProcAddress(s_imm_module, "ImmGetContext");
+      flImmSetCompositionWindow = (flTypeImmSetCompositionWindow)GetProcAddress(s_imm_module, "ImmSetCompositionWindow");
+***************
+*** 425,429 ****
+        }
+  
+!       TranslateMessage(&fl_msg);
+        DispatchMessageW(&fl_msg);
+        have_message = PeekMessageW(&fl_msg, NULL, 0, 0, PM_REMOVE);
+--- 430,439 ----
+        }
+  
+!       // Don't bother with key to character translation as we do
+!       // it manually for simpley keyboard widgets. In fact, calling
+!       // TranslateMessage() just makes it more difficult as it sets
+!       // a bunch of internal state.
+!       if (!use_simple_keyboard)
+!         TranslateMessage(&fl_msg);
+        DispatchMessageW(&fl_msg);
+        have_message = PeekMessageW(&fl_msg, NULL, 0, 0, PM_REMOVE);
+***************
+*** 543,546 ****
+--- 553,586 ----
+  };
+  
++ void fl_update_clipboard(void) {
++   HWND hwnd = fl_xid(Fl::first_window());
++ 
++   if (!hwnd)
++     return;
++ 
++   if (!OpenClipboard(hwnd))
++     return;
++ 
++   EmptyClipboard();
++ 
++   int utf16_len = fl_utf8toUtf16(fl_selection_buffer[1],
++                                  fl_selection_length[1], 0, 0);
++ 
++   HGLOBAL hMem = GlobalAlloc(GHND, utf16_len * 2 + 2); // moveable and zero'ed mem alloc.
++   LPVOID memLock = GlobalLock(hMem);
++ 
++   fl_utf8toUtf16(fl_selection_buffer[1], fl_selection_length[1],
++                  (unsigned short*) memLock, utf16_len + 1);
++ 
++   GlobalUnlock(hMem);
++   SetClipboardData(CF_UNICODETEXT, hMem);
++ 
++   CloseClipboard();
++ 
++   // In case Windows managed to lob of a WM_DESTROYCLIPBOARD during
++   // the above.
++   fl_i_own_selection[1] = 1;
++ }
++ 
+  // call this when you create a selection:
+  void Fl::copy(const char *stuff, int len, int clipboard) {
+***************
+*** 560,582 ****
+    fl_selection_buffer[clipboard][len] = 0; // needed for direct paste
+    fl_selection_length[clipboard] = len;
+!   if (clipboard) {
+!     // set up for "delayed rendering":
+!     if (OpenClipboard(NULL)) {
+!       // if the system clipboard works, use it
+!       int utf16_len = fl_utf8toUtf16(fl_selection_buffer[clipboard], fl_selection_length[clipboard], 0, 0);
+!       EmptyClipboard();
+!       HGLOBAL hMem = GlobalAlloc(GHND, utf16_len * 2 + 2); // moveable and zero'ed mem alloc.
+!       LPVOID memLock = GlobalLock(hMem);
+!       fl_utf8toUtf16(fl_selection_buffer[clipboard], fl_selection_length[clipboard], (unsigned short*) memLock, utf16_len + 1);
+!       GlobalUnlock(hMem);
+!       SetClipboardData(CF_UNICODETEXT, hMem);
+!       CloseClipboard();
+!       GlobalFree(hMem);
+!       fl_i_own_selection[clipboard] = 0;
+!     } else {
+!       // only if it fails, instruct paste() to use the internal buffers
+!       fl_i_own_selection[clipboard] = 1;
+!     }
+!   }
+  }
+  
+--- 600,606 ----
+    fl_selection_buffer[clipboard][len] = 0; // needed for direct paste
+    fl_selection_length[clipboard] = len;
+!   fl_i_own_selection[clipboard] = 1;
+!   if (clipboard)
+!     fl_update_clipboard();
+  }
+  
+***************
+*** 631,634 ****
+--- 655,690 ----
+  }
+  
++ static HWND clipboard_wnd = 0;
++ static HWND next_clipboard_wnd = 0;
++ 
++ static bool initial_clipboard = true;
++ 
++ void fl_clipboard_notify_change() {
++   // No need to do anything here...
++ }
++ 
++ void fl_clipboard_notify_target(HWND wnd) {
++   if (clipboard_wnd)
++     return;
++ 
++   // We get one fake WM_DRAWCLIPBOARD immediately, which we therefore
++   // need to ignore.
++   initial_clipboard = true;
++ 
++   clipboard_wnd = wnd;
++   next_clipboard_wnd = SetClipboardViewer(wnd);
++ }
++ 
++ void fl_clipboard_notify_untarget(HWND wnd) {
++   if (wnd != clipboard_wnd)
++     return;
++ 
++   ChangeClipboardChain(wnd, next_clipboard_wnd);
++   clipboard_wnd = next_clipboard_wnd = 0;
++ 
++   if (Fl::first_window())
++     fl_clipboard_notify_target(fl_xid(Fl::first_window()));
++ }
++ 
+  ////////////////////////////////////////////////////////////////
+  char fl_is_ime = 0;
+***************
+*** 650,653 ****
+--- 706,752 ----
+  }
+  
++ void fl_update_focus(void)
++ {
++   Fl_Widget *focus;
++   Fl_Window *win;
++ 
++   get_imm_module();
++ 
++   focus = Fl::grab();
++   if (!focus)
++     focus = Fl::focus();
++   if (!focus)
++     return;
++ 
++   // Grabs are special in that events are sent to the first
++   // available window
++   if (focus == Fl::grab())
++     win = Fl::first_window();
++   else {
++     win = focus->as_window();
++     if (!win)
++       win = focus->window();
++   }
++ 
++   if (!win) {
++     Fl::warning("Cannot find window for widget receiving focus");
++     return;
++   }
++ 
++   // No Win32 window created yet
++   if (!Fl_X::i(win) || !fl_xid(win))
++     return;
++ 
++   if (focus->simple_keyboard()) {
++     use_simple_keyboard = true;
++     if (flImmGetContext(fl_xid(win)) != 0)
++       flImmAssociateContextEx(fl_xid(win), 0, 0);
++   } else {
++     use_simple_keyboard = false;
++     if (flImmGetContext(fl_xid(win)) == 0)
++       flImmAssociateContextEx(fl_xid(win), 0, IACE_DEFAULT);
++   }
++ }
++ 
+  HWND fl_capture;
+  
+***************
+*** 797,800 ****
+--- 896,920 ----
+  }
+  
++ static xchar msdead2fltk(xchar in)
++ {
++   switch (in) {
++   case 0x0060:      // GRAVE ACCENT
++     return 0x0300;  // COMBINING GRAVE ACCENT
++   case 0x00b4:      // ACUTE ACCENT
++     return 0x0301;  // COMBINING ACUTE ACCENT
++   case 0x005e:      // CIRCUMFLEX ACCENT
++     return 0x0302;  // COMBINING CIRCUMFLEX ACCENT
++   case 0x007e:      // TILDE
++     return 0x0303;  // COMBINING TILDE
++   case 0x00a8:      // DIAERESIS
++     return 0x0308;  // COMBINING DIAERESIS
++   // FIXME: Windows dead key behaviour isn't documented and I don't have
++   //        any more keyboards to test with...
++   }
++ 
++   // hope that Windows gave us something proper to begin with
++   return in;
++ }
++ 
+  #if USE_COLORMAP
+  extern HPALETTE fl_select_palette(void); // in fl_color_win32.cxx
+***************
+*** 858,861 ****
+--- 978,983 ----
+    //fl_msg.lPrivate = ???
+  
++   MSG fl_orig_msg = fl_msg;
++ 
+    Fl_Window *window = fl_find(hWnd);
+  
+***************
+*** 1037,1057 ****
+      Fl::e_state = state;
+      static char buffer[1024];
+-     if (uMsg == WM_CHAR || uMsg == WM_SYSCHAR) {
+  
+        xchar u = (xchar) wParam;
+  //    Fl::e_length = fl_unicode2utf(&u, 1, buffer);
+        Fl::e_length = fl_utf8fromwc(buffer, 1024, &u, 1);
+        buffer[Fl::e_length] = 0;
+  
+! 
+!     } else if (Fl::e_keysym >= FL_KP && Fl::e_keysym <= FL_KP_Last) {
+!       if (state & FL_NUM_LOCK) {
+!         // Convert to regular keypress...
+! 	buffer[0] = Fl::e_keysym-FL_KP;
+! 	Fl::e_length = 1;
+!       } else {
+!         // Convert to special keypress...
+! 	buffer[0] = 0;
+! 	Fl::e_length = 0;
+  	switch (Fl::e_keysym) {
+  	  case FL_KP + '0' :
+--- 1159,1238 ----
+      Fl::e_state = state;
+      static char buffer[1024];
+  
++     if (use_simple_keyboard) {
++       BYTE keystate[256];
++       WCHAR wbuf[8];
++       int ret;
++ 
++       // I'm not sure if we ever get WM_CHAR (& friends) without an initial
++       // WM_KEYDOWN (& friends), but if we do then we should not send such
++       // side band events to simple keyboard widgets.
++       if ((fl_orig_msg.message != WM_KEYDOWN) &&
++           (fl_orig_msg.message != WM_SYSKEYDOWN) &&
++           (fl_orig_msg.message != WM_KEYUP) &&
++           (fl_orig_msg.message != WM_SYSKEYUP))
++         break;
++ 
++       GetKeyboardState(keystate);
++ 
++       // Pressing Ctrl wreaks havoc with the symbol lookup, so turn that off.
++       // But AltGr shows up as Ctrl+Alt in Windows, so keep Ctrl if Alt is
++       // active.
++       if (!(keystate[VK_MENU] & (1<<31)))
++         keystate[VK_CONTROL] = keystate[VK_LCONTROL] = keystate[VK_RCONTROL] = 0;
++ 
++       // We cannot inspect or modify Windows' internal state of the keyboard
++       // so we have to try to infer information from ToUnicode() and wedge
++       // things into a known state.
++       for (int i = 0;i < 2;i++) {
++         ret = ToUnicode(fl_orig_msg.wParam, 0, keystate, wbuf,
++                         sizeof(wbuf)/sizeof(wbuf[0]), 0);
++ 
++         // No symbol for this key (or unexpected length)
++         if ((ret == 0) || (ret < -1)) {
++           buffer[0] = 0;
++           Fl::e_length = 0;
++           break;
++         }
++ 
++         // A dead key. Convert this to a Unicode combining character so
++         // that the application can tell the difference between dead and
++         // normal keys.
++         if (ret == -1) {
++           xchar u = (xchar) msdead2fltk(wbuf[0]);
++           Fl::e_length = fl_utf8fromwc(buffer, 1024, &u, 1);
++           buffer[Fl::e_length] = 0;
++           break;
++         }
++ 
++         // If we have two characters (or more) from ToUnicode(), that's
++         // an invalid sequence. One character chould mean a proper symbol,
++         // or it could mean a composed one. In both cases we need to call
++         // ToUnicode() again to get something sane.
++         if (i == 0)
++           continue;
++ 
++         // We should now have something sane. Give whatever we have to the
++         // application.
++         Fl::e_length = fl_utf8fromwc(buffer, 1024, wbuf, ret);
++         buffer[Fl::e_length] = 0;
++       }
++     } else if (uMsg == WM_CHAR || uMsg == WM_SYSCHAR) {
+        xchar u = (xchar) wParam;
+  //    Fl::e_length = fl_unicode2utf(&u, 1, buffer);
+        Fl::e_length = fl_utf8fromwc(buffer, 1024, &u, 1);
+        buffer[Fl::e_length] = 0;
++     } else {
++       buffer[0] = 0;
++       Fl::e_length = 0;
++     }
+  
+!     // The keypad area is a bit odd in that we need to change the keysym
+!     // to properly indicate what the user meant, unlike other keys where
+!     // we normally change the text and keep keysym stable.
+!     if (Fl::e_keysym >= FL_KP && Fl::e_keysym <= FL_KP_Last) {
+!       // The initial mapping tables give us a keysym that corresponds to
+!       // numlock being on, so we only do something when it is off.
+!       if (!(state & FL_NUM_LOCK)) {
+  	switch (Fl::e_keysym) {
+  	  case FL_KP + '0' :
+***************
+*** 1085,1112 ****
+  	    Fl::e_keysym = FL_Delete;
+  	    break;
+- 	  case FL_KP + '/' :
+- 	  case FL_KP + '*' :
+- 	  case FL_KP + '-' :
+- 	  case FL_KP + '+' :
+- 	    buffer[0] = Fl::e_keysym-FL_KP;
+- 	    Fl::e_length = 1;
+- 	    break;
+  	}
+        }
+-     } else if ((lParam & (1<<31))==0) {
+- #ifdef FLTK_PREVIEW_DEAD_KEYS
+-       if ((lParam & (1<<24))==0) { // clear if dead key (always?)
+-         xchar u = (xchar) wParam;
+-         Fl::e_length = fl_utf8fromwc(buffer, 1024, &u, 1);
+-         buffer[Fl::e_length] = 0;
+-       } else { // set if "extended key" (never printable?)
+-         buffer[0] = 0;
+-         Fl::e_length = 0;
+-       }
+- #else
+-       buffer[0] = 0;
+-       Fl::e_length = 0;
+- #endif
+      }
+      Fl::e_text = buffer;
+      if (lParam & (1<<31)) { // key up events.
+--- 1266,1273 ----
+  	    Fl::e_keysym = FL_Delete;
+  	    break;
+  	}
+        }
+      }
++ 
+      Fl::e_text = buffer;
+      if (lParam & (1<<31)) { // key up events.
+***************
+*** 1126,1129 ****
+--- 1287,1291 ----
+      static int delta = 0; // running total of all motion
+      delta += (SHORT)(HIWORD(wParam));
++     Fl::e_dx = 0;
+      Fl::e_dy = -delta / WHEEL_DELTA;
+      delta += Fl::e_dy * WHEEL_DELTA;
+***************
+*** 1132,1135 ****
+--- 1294,1312 ----
+    }
+  
++ // This is only defined on Vista and upwards...
++ #ifndef WM_MOUSEHWHEEL
++ #define WM_MOUSEHWHEEL 0x020E
++ #endif
++ 
++   case WM_MOUSEHWHEEL: {
++     static int delta = 0; // running total of all motion
++     delta += (SHORT)(HIWORD(wParam));
++     Fl::e_dy = 0;
++     Fl::e_dx = delta / WHEEL_DELTA;
++     delta -= Fl::e_dx * WHEEL_DELTA;
++     if (Fl::e_dx) Fl::handle(FL_MOUSEWHEEL, window);
++     return 0;
++   }
++ 
+    case WM_GETMINMAXINFO:
+      Fl_X::i(window)->set_minmax((LPMINMAXINFO)lParam);
+***************
+*** 1186,1216 ****
+      return 1;
+  
+!   case WM_RENDERALLFORMATS:
+!     fl_i_own_selection[1] = 0;
+!     // Windoze seems unhappy unless I do these two steps. Documentation
+!     // seems to vary on whether opening the clipboard is necessary or
+!     // is in fact wrong:
+!     CloseClipboard();
+!     OpenClipboard(NULL);
+!     // fall through...
+!   case WM_RENDERFORMAT: {
+!     HANDLE h;
+! 
+! //  int l = fl_utf_nb_char((unsigned char*)fl_selection_buffer[1], fl_selection_length[1]);
+!     int l = fl_utf8toUtf16(fl_selection_buffer[1], fl_selection_length[1], NULL, 0); // Pass NULL buffer to query length required
+!     h = GlobalAlloc(GHND, (l+1) * sizeof(unsigned short));
+!     if (h) {
+!       unsigned short *g = (unsigned short*) GlobalLock(h);
+! //    fl_utf2unicode((unsigned char *)fl_selection_buffer[1], fl_selection_length[1], (xchar*)g);
+!       l = fl_utf8toUtf16(fl_selection_buffer[1], fl_selection_length[1], g, (l+1));
+!       g[l] = 0;
+!       GlobalUnlock(h);
+!       SetClipboardData(CF_UNICODETEXT, h);
+      }
+  
+!     // Windoze also seems unhappy if I don't do this. Documentation very
+!     // unclear on what is correct:
+!     if (fl_msg.message == WM_RENDERALLFORMATS) CloseClipboard();
+!     return 1;}
+  
+    default:
+--- 1363,1386 ----
+      return 1;
+  
+!   case WM_CHANGECBCHAIN:
+!     if ((hWnd == clipboard_wnd) &&
+!         (next_clipboard_wnd == (HWND)wParam)) {
+!       next_clipboard_wnd = (HWND)lParam;
+!       return 0;
+      }
++     break;
++ 
++   case WM_DRAWCLIPBOARD:
++     // When the clipboard moves between two FLTK windows,
++     // fl_i_own_selection will temporarily be false as we are
++     // processing this message. Hence the need to use fl_find().
++     if (!initial_clipboard && !fl_find(GetClipboardOwner()))
++       fl_trigger_clipboard_notify(1);
++     initial_clipboard = false;
+  
+!     if (next_clipboard_wnd)
+!       SendMessage(next_clipboard_wnd, WM_DRAWCLIPBOARD, wParam, lParam);
+! 
+!     return 0;
+  
+    default:
+***************
+*** 1321,1324 ****
+--- 1491,1499 ----
+    Y+=yoff;
+  
++   if (w->flags() & Fl_Widget::FULLSCREEN) {
++     X = Y = 0;
++     bx = by = bt = 0;
++   }
++ 
+    return ret;
+  }
+***************
+*** 1371,1374 ****
+--- 1546,1601 ----
+  }
+  
++ static void make_fullscreen(Fl_Window *w, Window xid, int X, int Y, int W, int H) {
++   int sx, sy, sw, sh;
++   Fl::screen_xywh(sx, sy, sw, sh, X, Y, W, H);
++   DWORD flags = GetWindowLong(xid, GWL_STYLE);
++   flags = flags & ~(WS_THICKFRAME|WS_CAPTION);
++   SetWindowLong(xid, GWL_STYLE, flags);
++   // SWP_NOSENDCHANGING is so that we can override size limits
++   SetWindowPos(xid, HWND_TOP, sx, sy, sw, sh, SWP_NOSENDCHANGING | SWP_FRAMECHANGED);
++ }
++ 
++ void fullscreen_x(Fl_Window *w) {
++   w->_set_fullscreen();
++   make_fullscreen(w, fl_xid(w), w->x(), w->y(), w->w(), w->h());
++   Fl::handle(FL_FULLSCREEN, w);
++ }
++ 
++ void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H) {
++   w->_clear_fullscreen();
++   DWORD style = GetWindowLong(fl_xid(w), GWL_STYLE);
++   // Remove the xid temporarily so that Fl_X::fake_X_wm() behaves like it
++   // does in Fl_X::make().
++   HWND xid = fl_xid(w);
++   Fl_X::i(w)->xid = NULL;
++   int x, y, bt, bx, by;
++   switch (Fl_X::fake_X_wm(w, x, y, bt, bx, by)) {
++   case 0: 
++     break;
++   case 1: 
++     style |= WS_CAPTION; 
++     break;
++   case 2: 
++     if (w->border()) {
++       style |= WS_THICKFRAME | WS_CAPTION; 
++     }
++     break;
++   }
++   Fl_X::i(w)->xid = xid;
++   // Adjust for decorations (but not if that puts the decorations
++   // outside the screen)
++   if ((X != w->x()) || (Y != w->y())) {
++     X -= bx;
++     Y -= by+bt;
++   }
++   W += bx*2;
++   H += by*2+bt;
++   SetWindowLong(fl_xid(w), GWL_STYLE, style);
++   SetWindowPos(fl_xid(w), 0, X, Y, W, H,
++                SWP_NOACTIVATE | SWP_NOZORDER | SWP_FRAMECHANGED);
++   Fl::handle(FL_FULLSCREEN, w);
++ }
++ 
++ 
+  ////////////////////////////////////////////////////////////////
+  
+***************
+*** 1409,1413 ****
+  char fl_show_iconic;	// hack for Fl_Window::iconic()
+  // int fl_background_pixel = -1; // color to use for background
+- HCURSOR fl_default_cursor;
+  UINT fl_wake_msg = 0;
+  int fl_disable_transient_for; // secret method of removing TRANSIENT_FOR
+--- 1636,1639 ----
+***************
+*** 1457,1461 ****
+        w->icon((void *)LoadIcon(NULL, IDI_APPLICATION));
+      wcw.hIcon = wcw.hIconSm = (HICON)w->icon();
+!     wcw.hCursor = fl_default_cursor = LoadCursor(NULL, IDC_ARROW);
+      //uchar r,g,b; Fl::get_color(FL_GRAY,r,g,b);
+      //wc.hbrBackground = (HBRUSH)CreateSolidBrush(RGB(r,g,b));
+--- 1683,1687 ----
+        w->icon((void *)LoadIcon(NULL, IDI_APPLICATION));
+      wcw.hIcon = wcw.hIconSm = (HICON)w->icon();
+!     wcw.hCursor = LoadCursor(NULL, IDC_ARROW);
+      //uchar r,g,b; Fl::get_color(FL_GRAY,r,g,b);
+      //wc.hbrBackground = (HBRUSH)CreateSolidBrush(RGB(r,g,b));
+***************
+*** 1500,1515 ****
+      switch (fake_X_wm(w, xwm, ywm, bt, bx, by)) {
+        // No border (used for menus)
+!       case 0: style |= WS_POPUP;
+!               styleEx |= WS_EX_TOOLWINDOW;
+  	      break;
+  
+        // Thin border and title bar
+!       case 1: style |= WS_DLGFRAME | WS_CAPTION; break;
+  
+        // Thick, resizable border and title bar, with maximize button
+!       case 2: style |= WS_THICKFRAME | WS_MAXIMIZEBOX | WS_CAPTION ; break;
+      }
+      if (by+bt) {
+-       if (!w->modal()) style |= WS_SYSMENU | WS_MINIMIZEBOX;
+        wp += 2*bx;
+        hp += 2*by+bt;
+--- 1726,1749 ----
+      switch (fake_X_wm(w, xwm, ywm, bt, bx, by)) {
+        // No border (used for menus)
+!       case 0:
+!         style |= WS_POPUP;
+!         styleEx |= WS_EX_TOOLWINDOW;
+  	      break;
+  
+        // Thin border and title bar
+!       case 1:
+!         style |= WS_DLGFRAME | WS_CAPTION;
+!         if (!w->modal())
+!           style |= WS_SYSMENU | WS_MINIMIZEBOX;
+!         break;
+  
+        // Thick, resizable border and title bar, with maximize button
+!       case 2:
+!         style |= WS_THICKFRAME | WS_SYSMENU | WS_MAXIMIZEBOX | WS_CAPTION;
+!         if (!w->modal())
+!           style |= WS_MINIMIZEBOX;
+!         break;
+      }
+      if (by+bt) {
+        wp += 2*bx;
+        hp += 2*by+bt;
+***************
+*** 1541,1545 ****
+    x->region = 0;
+    x->private_dc = 0;
+!   x->cursor = fl_default_cursor;
+    if (!fl_codepage) fl_get_codepage();
+  
+--- 1775,1779 ----
+    x->region = 0;
+    x->private_dc = 0;
+!   x->cursor = LoadCursor(NULL, IDC_ARROW);
+    if (!fl_codepage) fl_get_codepage();
+  
+***************
+*** 1567,1573 ****
+--- 1801,1821 ----
+    if (lab) free(lab);
+  
++   if (w->flags() & Fl_Widget::FULLSCREEN) {
++   /* We need to make sure that the fullscreen is created on the
++      default monitor, ie the desktop where the shortcut is located
++      etc. This requires that CreateWindow is called with CW_USEDEFAULT
++      for x and y. We can then use GetWindowRect to determine which
++      monitor the window was placed on. */
++     RECT rect;
++     GetWindowRect(x->xid, &rect);
++     make_fullscreen(w, x->xid, rect.left, rect.top, 
++                     rect.right - rect.left, rect.bottom - rect.top);
++   }
++ 
+    x->next = Fl_X::first;
+    Fl_X::first = x;
+  
++   fl_clipboard_notify_target(x->xid);
++ 
+    x->wait_for_expose = 1;
+    if (fl_show_iconic) {showit = 0; fl_show_iconic = 0;}
+***************
+*** 1582,1586 ****
+    // other windows from the code, or we lose the capture.
+    ShowWindow(x->xid, !showit ? SW_SHOWMINNOACTIVE :
+! 	     (Fl::grab() || (style & WS_POPUP)) ? SW_SHOWNOACTIVATE : SW_SHOWNORMAL);
+  
+    // Register all windows for potential drag'n'drop operations
+--- 1830,1834 ----
+    // other windows from the code, or we lose the capture.
+    ShowWindow(x->xid, !showit ? SW_SHOWMINNOACTIVE :
+! 	     (Fl::grab() || (styleEx & WS_EX_TOOLWINDOW)) ? SW_SHOWNOACTIVATE : SW_SHOWNORMAL);
+  
+    // Register all windows for potential drag'n'drop operations
+***************
+*** 1778,1781 ****
+--- 2026,2152 ----
+  
+  ////////////////////////////////////////////////////////////////
++ 
++ #ifndef IDC_HAND
++ #  define IDC_HAND  MAKEINTRESOURCE(32649)
++ #endif // !IDC_HAND
++ 
++ int Fl_X::set_cursor(Fl_Cursor c) {
++   LPSTR n;
++ 
++   if (c == FL_CURSOR_NONE)
++     cursor = NULL;
++   else {
++     switch (c) {
++     case FL_CURSOR_ARROW:   n = IDC_ARROW; break;
++     case FL_CURSOR_CROSS:   n = IDC_CROSS; break;
++     case FL_CURSOR_WAIT:    n = IDC_WAIT; break;
++     case FL_CURSOR_INSERT:  n = IDC_IBEAM; break;
++     case FL_CURSOR_HAND:    n = IDC_HAND; break;
++     case FL_CURSOR_HELP:    n = IDC_HELP; break;
++     case FL_CURSOR_MOVE:    n = IDC_SIZEALL; break;
++     case FL_CURSOR_N:
++     case FL_CURSOR_S:
++       // FIXME: Should probably have fallbacks for these instead
++     case FL_CURSOR_NS:      n = IDC_SIZENS; break;
++     case FL_CURSOR_NE:
++     case FL_CURSOR_SW:
++       // FIXME: Dito.
++     case FL_CURSOR_NESW:    n = IDC_SIZENESW; break;
++     case FL_CURSOR_E:
++     case FL_CURSOR_W:
++       // FIXME: Dito.
++     case FL_CURSOR_WE:      n = IDC_SIZEWE; break;
++     case FL_CURSOR_SE:
++     case FL_CURSOR_NW:
++       // FIXME: Dito.
++     case FL_CURSOR_NWSE:    n = IDC_SIZENWSE; break;
++     default:
++       return 0;
++     }
++ 
++     cursor = LoadCursor(NULL, n);
++     if (cursor == NULL)
++       return 0;
++   }
++ 
++   SetCursor(cursor);
++ 
++   return 1;
++ }
++ 
++ int Fl_X::set_cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
++   BITMAPV5HEADER bi;
++   HBITMAP bitmap, mask;
++   DWORD *bits;
++ 
++   if ((hotx < 0) || (hotx >= image->w()))
++     return 0;
++   if ((hoty < 0) || (hoty >= image->h()))
++     return 0;
++ 
++   memset(&bi, 0, sizeof(BITMAPV5HEADER));
++ 
++   bi.bV5Size        = sizeof(BITMAPV5HEADER);
++   bi.bV5Width       = image->w();
++   bi.bV5Height      = image->h();
++   bi.bV5Planes      = 1;
++   bi.bV5BitCount    = 32;
++   bi.bV5Compression = BI_BITFIELDS;
++   bi.bV5RedMask     = 0x00FF0000;
++   bi.bV5GreenMask   = 0x0000FF00;
++   bi.bV5BlueMask    = 0x000000FF;
++   bi.bV5AlphaMask   = 0xFF000000;
++ 
++   HDC hdc;
++ 
++   hdc = GetDC(NULL);
++   bitmap = CreateDIBSection(hdc, (BITMAPINFO*)&bi, DIB_RGB_COLORS, (void**)&bits, NULL, 0);
++   ReleaseDC(NULL, hdc);
++ 
++   const uchar *i = (const uchar*)*image->data();
++   for (int y = 0;y < image->h();y++) {
++     for (int x = 0;x < image->w();x++) {
++       switch (image->d()) {
++       case 1:
++         *bits = (0xff<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
++         break;
++       case 2:
++         *bits = (i[1]<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
++         break;
++       case 3:
++         *bits = (0xff<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
++         break;
++       case 4:
++         *bits = (i[3]<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
++         break;
++       }
++       i += image->d();
++       bits++;
++     }
++     i += image->ld();
++   }
++ 
++   // A mask bitmap is still needed even though it isn't used
++   mask = CreateBitmap(image->w(),image->h(),1,1,NULL);
++ 
++   ICONINFO ii;
++ 
++   ii.fIcon    = FALSE;
++   ii.xHotspot = hotx;
++   ii.yHotspot = hoty;
++   ii.hbmMask  = mask;
++   ii.hbmColor = bitmap;
++ 
++   cursor = CreateIconIndirect(&ii);
++ 
++   DeleteObject(bitmap);
++   DeleteObject(mask);
++ 
++   SetCursor(cursor);
++ 
++   return 1;
++ }
++ 
++ ////////////////////////////////////////////////////////////////
+  // Implement the virtual functions for the base Fl_Window class:
+  
+*** fltk-1.3.0/src/Fl_x.cxx	2011-05-30 11:47:48.000000000 -0500
+--- fltk-1.3.0.new/src/Fl_x.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 53,56 ****
+--- 53,65 ----
+  #  include <X11/Xlib.h>
+  #  include <X11/keysym.h>
++ #  include <X11/cursorfont.h>
++ 
++ #  if HAVE_XCURSOR
++ #    include <X11/Xcursor/Xcursor.h>
++ #  endif
++ 
++ #  ifdef HAVE_XFIXES
++ #  include <X11/extensions/Xfixes.h>
++ #  endif
+  
+  static Fl_Xlib_Graphics_Driver fl_xlib_driver;
+***************
+*** 301,306 ****
+--- 310,318 ----
+  XIM fl_xim_im = 0;
+  XIC fl_xim_ic = 0;
++ Window fl_xim_win = 0;
+  char fl_is_over_the_spot = 0;
+  static XRectangle status_area;
++ static bool have_xfixes = false;
++ static int xfixes_event_base = 0;
+  
+  static Atom WM_DELETE_WINDOW;
+***************
+*** 309,312 ****
+--- 321,327 ----
+  static Atom TARGETS;
+  static Atom CLIPBOARD;
++ static Atom TIMESTAMP;
++ static Atom PRIMARY_TIMESTAMP;
++ static Atom CLIPBOARD_TIMESTAMP;
+  Atom fl_XdndAware;
+  Atom fl_XdndSelection;
+***************
+*** 329,332 ****
+--- 344,350 ----
+  Atom fl_NET_WM_NAME;			// utf8 aware window label
+  Atom fl_NET_WM_ICON_NAME;		// utf8 aware window icon name
++ Atom fl_NET_SUPPORTING_WM_CHECK;
++ Atom fl_NET_WM_STATE;
++ Atom fl_NET_WM_STATE_FULLSCREEN;
+  
+  /*
+***************
+*** 582,585 ****
+--- 600,662 ----
+  }
+  
++ void fl_xim_deactivate(void);
++ 
++ void fl_xim_activate(Window xid)
++ {
++   if (!fl_xim_im)
++     return;
++ 
++   // If the focused window has changed, then use the brute force method
++   // of completely recreating the input context.
++   if (fl_xim_win != xid) {
++     fl_xim_deactivate();
++ 
++     fl_new_ic();
++     fl_xim_win = xid;
++ 
++     XSetICValues(fl_xim_ic,
++                  XNFocusWindow, fl_xim_win,
++                  XNClientWindow, fl_xim_win,
++                  NULL);
++   }
++ 
++   fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
++ }
++ 
++ void fl_xim_deactivate(void)
++ {
++   if (!fl_xim_ic)
++     return;
++ 
++   XDestroyIC(fl_xim_ic);
++   fl_xim_ic = NULL;
++ 
++   fl_xim_win = 0;
++ }
++ 
++ extern Fl_Window *fl_xfocus;
++ 
++ void fl_update_focus(void)
++ {
++   Fl_Widget *focus;
++ 
++   focus = Fl::grab();
++   if (!focus)
++     focus = Fl::focus();
++   if (!focus)
++     return;
++ 
++   if (focus->simple_keyboard()) {
++     fl_xim_deactivate();
++   } else {
++     // fl_xfocus should always be set if something has focus, but let's
++     // play it safe
++     if (!fl_xfocus || !fl_xid(fl_xfocus))
++       return;
++ 
++     fl_xim_activate(fl_xid(fl_xfocus));
++   }
++ }
++ 
+  void fl_open_display() {
+    if (fl_display) return;
+***************
+*** 605,608 ****
+--- 682,688 ----
+    TARGETS               = XInternAtom(d, "TARGETS",             0);
+    CLIPBOARD             = XInternAtom(d, "CLIPBOARD",           0);
++   TIMESTAMP             = XInternAtom(d, "TIMESTAMP",           0);
++   PRIMARY_TIMESTAMP     = XInternAtom(d, "PRIMARY_TIMESTAMP",   0);
++   CLIPBOARD_TIMESTAMP   = XInternAtom(d, "CLIPBOARD_TIMESTAMP", 0);
+    fl_XdndAware          = XInternAtom(d, "XdndAware",           0);
+    fl_XdndSelection      = XInternAtom(d, "XdndSelection",       0);
+***************
+*** 626,629 ****
+--- 706,712 ----
+    fl_NET_WM_NAME        = XInternAtom(d, "_NET_WM_NAME",        0);
+    fl_NET_WM_ICON_NAME   = XInternAtom(d, "_NET_WM_ICON_NAME",   0);
++   fl_NET_SUPPORTING_WM_CHECK = XInternAtom(d, "_NET_SUPPORTING_WM_CHECK", 0);
++   fl_NET_WM_STATE       = XInternAtom(d, "_NET_WM_STATE",       0);
++   fl_NET_WM_STATE_FULLSCREEN = XInternAtom(d, "_NET_WM_STATE_FULLSCREEN", 0);
+  
+    if (sizeof(Atom) < 4)
+***************
+*** 647,650 ****
+--- 730,741 ----
+    Fl::visual(FL_RGB);
+  #endif
++ 
++ #ifdef HAVE_XFIXES
++   int error_base;
++   if (XFixesQueryExtension(d, &xfixes_event_base, &error_base))
++     have_xfixes = true;
++   else
++     have_xfixes = false;
++ #endif
+  }
+  
+***************
+*** 769,772 ****
+--- 860,888 ----
+  }
+  
++ 
++ /* 
++    Get window property value (32 bit format) 
++    Returns zero on success, -1 on error
++ */
++ static int get_xwinprop(Window wnd, Atom prop, long max_length,
++                         unsigned long *nitems, unsigned long **data) {
++   Atom actual;
++   int format;
++   unsigned long bytes_after;
++   
++   if (Success != XGetWindowProperty(fl_display, wnd, prop, 0, max_length, 
++                                     False, AnyPropertyType, &actual, &format, 
++                                     nitems, &bytes_after, (unsigned char**)data)) {
++     return -1;
++   }
++ 
++   if (actual == None || format != 32) {
++     return -1;
++   }
++ 
++   return 0;
++ }
++ 
++ 
+  ////////////////////////////////////////////////////////////////
+  // Code for copying to clipboard and DnD out of the program:
+***************
+*** 788,791 ****
+--- 904,995 ----
+  
+  ////////////////////////////////////////////////////////////////
++ // Code for tracking clipboard changes:
++ 
++ static Time primary_timestamp = -1;
++ static Time clipboard_timestamp = -1;
++ 
++ extern bool fl_clipboard_notify_empty(void);
++ extern void fl_trigger_clipboard_notify(int source);
++ 
++ static void poll_clipboard_owner(void) {
++   Window xid;
++ 
++   // No polling needed with Xfixes
++   if (have_xfixes)
++     return;
++ 
++   // No one is interested, so no point polling
++   if (fl_clipboard_notify_empty())
++     return;
++ 
++   // We need a window for this to work
++   if (!Fl::first_window())
++     return;
++   xid = fl_xid(Fl::first_window());
++   if (!xid)
++     return;
++ 
++   // Request an update of the selection time for both the primary and
++   // clipboard selections. Magic continues when we get a SelectionNotify.
++   if (!fl_i_own_selection[0])
++     XConvertSelection(fl_display, XA_PRIMARY, TIMESTAMP, PRIMARY_TIMESTAMP,
++                       xid, fl_event_time);
++   if (!fl_i_own_selection[1])
++     XConvertSelection(fl_display, CLIPBOARD, TIMESTAMP, CLIPBOARD_TIMESTAMP,
++                       xid, fl_event_time);
++ }
++ 
++ static void clipboard_timeout(void *data)
++ {
++   // No one is interested, so stop polling
++   if (fl_clipboard_notify_empty())
++     return;
++ 
++   poll_clipboard_owner();
++ 
++   Fl::repeat_timeout(0.5, clipboard_timeout);
++ }
++ 
++ static void handle_clipboard_timestamp(int clipboard, Time time)
++ {
++   Time *timestamp;
++ 
++   timestamp = clipboard ? &clipboard_timestamp : &primary_timestamp;
++ 
++   if (!have_xfixes) {
++     // Initial scan, just store the value
++     if (*timestamp == (Time)-1) {
++       *timestamp = time;
++       return;
++     }
++   }
++ 
++   // Same selection
++   if (time == *timestamp)
++     return;
++ 
++   *timestamp = time;
++ 
++   // Something happened! Let's tell someone!
++   fl_trigger_clipboard_notify(clipboard);
++ }
++ 
++ void fl_clipboard_notify_change() {
++   // Reset the timestamps if we've going idle so that you don't
++   // get a bogus immediate trigger next time they're activated.
++   if (fl_clipboard_notify_empty()) {
++     primary_timestamp = -1;
++     clipboard_timestamp = -1;
++   } else {
++     if (!have_xfixes) {
++       poll_clipboard_owner();
++ 
++       if (!Fl::has_timeout(clipboard_timeout))
++         Fl::add_timeout(0.5, clipboard_timeout);
++     }
++   }
++ }
++ 
++ ////////////////////////////////////////////////////////////////
+  
+  const XEvent* fl_xevent; // the current x event
+***************
+*** 865,872 ****
+    fl_xevent = &thisevent;
+    Window xid = xevent.xany.window;
+-   static Window xim_win = 0;
+  
+    if (fl_xim_ic && xevent.type == DestroyNotify &&
+!         xid != xim_win && !fl_find(xid))
+    {
+      XIM xim_im;
+--- 1069,1075 ----
+    fl_xevent = &thisevent;
+    Window xid = xevent.xany.window;
+  
+    if (fl_xim_ic && xevent.type == DestroyNotify &&
+!         xid != fl_xim_win && !fl_find(xid))
+    {
+      XIM xim_im;
+***************
+*** 883,929 ****
+    }
+  
+!   if (fl_xim_ic && (xevent.type == FocusIn))
+!   {
+! #define POOR_XIM
+! #ifdef POOR_XIM
+!         if (xim_win != xid)
+!         {
+!                 xim_win  = xid;
+!                 XDestroyIC(fl_xim_ic);
+!                 fl_xim_ic = NULL;
+!                 fl_new_ic();
+!                 XSetICValues(fl_xim_ic,
+!                                 XNFocusWindow, xevent.xclient.window,
+!                                 XNClientWindow, xid,
+!                                 NULL);
+!         }
+!         fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
+! #else
+!     if (Fl::first_window() && Fl::first_window()->modal()) {
+!       Window x  = fl_xid(Fl::first_window());
+!       if (x != xim_win) {
+!         xim_win  = x;
+!         XSetICValues(fl_xim_ic,
+!                         XNFocusWindow, xim_win,
+!                         XNClientWindow, xim_win,
+!                         NULL);
+!         fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
+!       }
+!     } else if (xim_win != xid && xid) {
+!       xim_win = xid;
+!       XSetICValues(fl_xim_ic,
+!                         XNFocusWindow, xevent.xclient.window,
+!                         XNClientWindow, xid,
+!                         //XNFocusWindow, xim_win,
+!                         //XNClientWindow, xim_win,
+!                         NULL);
+!       fl_set_spot(spotf, spots, spot.x, spot.y, spot.width, spot.height);
+!     }
+! #endif
+    }
+  
+-   if ( XFilterEvent((XEvent *)&xevent, 0) )
+-       return(1);
+- 
+    switch (xevent.type) {
+  
+--- 1086,1094 ----
+    }
+  
+!   if (fl_xim_ic) {
+!     if (XFilterEvent((XEvent *)&xevent, 0))
+!       return 1;
+    }
+  
+    switch (xevent.type) {
+  
+***************
+*** 937,941 ****
+  
+    case SelectionNotify: {
+-     if (!fl_selection_requestor) return 0;
+      static unsigned char* buffer = 0;
+      if (buffer) {XFree(buffer); buffer = 0;}
+--- 1102,1105 ----
+***************
+*** 953,956 ****
+--- 1117,1133 ----
+                               &actual, &format, &count, &remaining,
+                               &portion)) break; // quit on error
++ 
++       if ((fl_xevent->xselection.property == PRIMARY_TIMESTAMP) ||
++           (fl_xevent->xselection.property == CLIPBOARD_TIMESTAMP)) {
++         if (portion && format == 32 && count == 1) {
++           Time t = *(unsigned int*)portion;
++           if (fl_xevent->xselection.property == CLIPBOARD_TIMESTAMP)
++             handle_clipboard_timestamp(1, t);
++           else
++             handle_clipboard_timestamp(0, t);
++         }
++         return true;
++       }
++ 
+        if (actual == TARGETS || actual == XA_ATOM) {
+  	Atom type = XA_STRING;
+***************
+*** 989,992 ****
+--- 1166,1172 ----
+        convert_crlf(buffer, bytesread);
+      }
++ 
++     if (!fl_selection_requestor) return 0;
++ 
+      Fl::e_text = buffer ? (char*)buffer : (char *)"";
+      Fl::e_length = bytesread;
+***************
+*** 1009,1012 ****
+--- 1189,1193 ----
+      int clipboard = fl_xevent->xselectionclear.selection == CLIPBOARD;
+      fl_i_own_selection[clipboard] = 0;
++     poll_clipboard_owner();
+      return 1;}
+  
+***************
+*** 1221,1224 ****
+--- 1402,1408 ----
+      if (fl_xim_ic) XSetICFocus(fl_xim_ic);
+      event = FL_FOCUS;
++     // If the user has toggled from another application to this one,
++     // then it's a good time to check for clipboard changes.
++     poll_clipboard_owner();
+      break;
+  
+***************
+*** 1261,1273 ****
+          len = XLookupString((XKeyEvent*)&(xevent.xkey),
+                               buffer, buffer_len, &keysym, 0/*&compose*/);
+!         if (keysym && keysym < 0x400) { // a character in latin-1,2,3,4 sets
+!           // force it to type a character (not sure if this ever is needed):
+!           // if (!len) {buffer[0] = char(keysym); len = 1;}
+!           len = fl_utf8encode(XKeysymToUcs(keysym), buffer);
+!           if (len < 1) len = 1;
+!           // ignore all effects of shift on the keysyms, which makes it a lot
+!           // easier to program shortcuts and is Windoze-compatible:
+!           keysym = XKeycodeToKeysym(fl_display, keycode, 0);
+!         }
+        }
+        // MRS: Can't use Fl::event_state(FL_CTRL) since the state is not
+--- 1445,1457 ----
+          len = XLookupString((XKeyEvent*)&(xevent.xkey),
+                               buffer, buffer_len, &keysym, 0/*&compose*/);
+!         // XLookupString() is only defined to return Latin-1 (although it
+!         // often gives you more). To be safe, use our own lookups based on
+!         // keysym.
+!         len = fl_utf8encode(XKeysymToUcs(keysym), buffer);
+!         if (len < 1)
+!           len = 1;
+!         // ignore all effects of shift on the keysyms, which makes it a lot
+!         // easier to program shortcuts and is Windoze-compatable:
+!         keysym = XKeycodeToKeysym(fl_display, keycode, 0);
+        }
+        // MRS: Can't use Fl::event_state(FL_CTRL) since the state is not
+***************
+*** 1441,1444 ****
+--- 1625,1629 ----
+      Fl::e_keysym = FL_Button + xevent.xbutton.button;
+      set_event_xy();
++     Fl::e_dx = Fl::e_dy = 0;
+      if (xevent.xbutton.button == Button4) {
+        Fl::e_dy = -1; // Up
+***************
+*** 1447,1450 ****
+--- 1632,1641 ----
+        Fl::e_dy = +1; // Down
+        event = FL_MOUSEWHEEL;
++     } else if (xevent.xbutton.button == 6) {
++       Fl::e_dx = -1; // Left
++       event = FL_MOUSEWHEEL;
++     } else if (xevent.xbutton.button == 7) {
++       Fl::e_dx = +1; // Right
++       event = FL_MOUSEWHEEL;
+      } else {
+        Fl::e_state |= (FL_BUTTON1 << (xevent.xbutton.button-1));
+***************
+*** 1457,1460 ****
+--- 1648,1676 ----
+      break;
+  
++   case PropertyNotify:
++     if (xevent.xproperty.atom == fl_NET_WM_STATE) {
++       int fullscreen_state = 0;
++       if (xevent.xproperty.state != PropertyDelete) {
++         unsigned long nitems;
++         unsigned long *words = 0;
++         if (0 == get_xwinprop(xid, fl_NET_WM_STATE, 64, &nitems, &words) ) { 
++           for (unsigned long item = 0; item < nitems; item++) {
++             if (words[item] == fl_NET_WM_STATE_FULLSCREEN) {
++               fullscreen_state = 1;
++             }
++           }
++         }
++       }
++       if (window->fullscreen_active() && !fullscreen_state) {
++         window->_clear_fullscreen();
++         event = FL_FULLSCREEN;
++       }
++       if (!window->fullscreen_active() && fullscreen_state) {
++         window->_set_fullscreen();
++         event = FL_FULLSCREEN;
++       }
++     }
++     break;
++ 
+    case MotionNotify:
+      set_event_xy();
+***************
+*** 1557,1560 ****
+--- 1773,1795 ----
+    }
+  
++ #ifdef HAVE_XFIXES
++   switch (xevent.type - xfixes_event_base) {
++   case XFixesSelectionNotify: {
++     // Someone feeding us bogus events?
++     if (!have_xfixes)
++       return true;
++ 
++     XFixesSelectionNotifyEvent *selection_notify = (XFixesSelectionNotifyEvent *)&xevent;
++ 
++     if ((selection_notify->selection == XA_PRIMARY) && !fl_i_own_selection[0])
++       handle_clipboard_timestamp(0, selection_notify->selection_timestamp);
++     else if ((selection_notify->selection == CLIPBOARD) && !fl_i_own_selection[1])
++       handle_clipboard_timestamp(1, selection_notify->selection_timestamp);
++ 
++     return true;
++     }
++   }
++ #endif
++ 
+    return Fl::handle(event, window);
+  }
+***************
+*** 1596,1599 ****
+--- 1831,1903 ----
+  ////////////////////////////////////////////////////////////////
+  
++ #define _NET_WM_STATE_REMOVE        0  /* remove/unset property */
++ #define _NET_WM_STATE_ADD           1  /* add/set property */
++ #define _NET_WM_STATE_TOGGLE        2  /* toggle property  */
++ 
++ static void send_wm_state_event(Window wnd, int add, Atom prop) {
++   XEvent e;
++   e.xany.type = ClientMessage;
++   e.xany.window = wnd;
++   e.xclient.message_type = fl_NET_WM_STATE;
++   e.xclient.format = 32;
++   e.xclient.data.l[0] = add ? _NET_WM_STATE_ADD : _NET_WM_STATE_REMOVE;
++   e.xclient.data.l[1] = prop;
++   e.xclient.data.l[2] = 0;
++   e.xclient.data.l[3] = 0;
++   e.xclient.data.l[4] = 0;
++   XSendEvent(fl_display, RootWindow(fl_display, fl_screen),
++              0, SubstructureNotifyMask | SubstructureRedirectMask,
++              &e);
++ }
++ 
++ int ewmh_supported() {
++   static int result = -1;
++ 
++   if (result == -1) {
++     result = 0;
++     unsigned long nitems;
++     unsigned long *words = 0;
++     if (0 == get_xwinprop(XRootWindow(fl_display, fl_screen), fl_NET_SUPPORTING_WM_CHECK, 64,
++                           &nitems, &words) && nitems == 1) {
++       Window child = words[0];
++       if (0 == get_xwinprop(child, fl_NET_SUPPORTING_WM_CHECK, 64,
++                            &nitems, &words) && nitems == 1) {
++         result = (child == words[0]);
++       }
++     }
++   }
++ 
++   return result;
++ }
++ 
++ /* Change an existing window to fullscreen */
++ void fullscreen_x(Fl_Window *w) {
++   if (ewmh_supported()) {
++     send_wm_state_event(fl_xid(w), 1, fl_NET_WM_STATE_FULLSCREEN);
++   } else {
++     w->_set_fullscreen();
++     w->hide();
++     w->show();
++     /* We want to grab the window, not a widget, so we cannot use Fl::grab */
++     XGrabKeyboard(fl_display, fl_xid(w), 1, GrabModeAsync, GrabModeAsync, fl_event_time);
++     Fl::handle(FL_FULLSCREEN, w);
++   }
++ }
++ 
++ void fullscreen_off_x(Fl_Window *w, int X, int Y, int W, int H) {
++   if (ewmh_supported()) {
++     send_wm_state_event(fl_xid(w), 0, fl_NET_WM_STATE_FULLSCREEN);
++   } else {
++     w->_clear_fullscreen();
++     /* The grab will be lost when the window is destroyed */
++     w->hide();
++     w->resize(X,Y,W,H);
++     w->show();
++     Fl::handle(FL_FULLSCREEN, w);
++   }
++ }
++ 
++ ////////////////////////////////////////////////////////////////
++ 
+  // A subclass of Fl_Window may call this to associate an X window it
+  // creates with the Fl_Window:
+***************
+*** 1631,1634 ****
+--- 1935,1939 ----
+  |ButtonPressMask|ButtonReleaseMask
+  |EnterWindowMask|LeaveWindowMask
++ |PropertyChangeMask
+  |PointerMotionMask;
+  
+***************
+*** 1702,1705 ****
+--- 2007,2020 ----
+      if (!win->border()) {attr.override_redirect = 1; mask |= CWOverrideRedirect;}
+    }
++   // For the non-EWMH fullscreen case, we cannot use the code above,
++   // since we do not want save_under, do not want to turn off the
++   // border, and cannot grab without an existing window. Besides, 
++   // there is no clear_override(). 
++   if (win->flags() & Fl_Widget::FULLSCREEN && !ewmh_supported()) {
++     attr.override_redirect = 1;
++     mask |= CWOverrideRedirect;
++     Fl::screen_xywh(X, Y, W, H, X, Y, W, H);
++   }
++ 
+    if (fl_background_pixel >= 0) {
+      attr.background_pixel = fl_background_pixel;
+***************
+*** 1761,1764 ****
+--- 2076,2085 ----
+      }
+  
++     // If asked for, create fullscreen
++     if (win->flags() & Fl_Widget::FULLSCREEN && ewmh_supported()) {
++       XChangeProperty (fl_display, xp->xid, fl_NET_WM_STATE, XA_ATOM, 32,
++                        PropModeAppend, (unsigned char*) &fl_NET_WM_STATE_FULLSCREEN, 1);
++     }
++ 
+      // Make it receptive to DnD:
+      long version = 4;
+***************
+*** 1790,1793 ****
+--- 2111,2124 ----
+    }
+  
++ #ifdef HAVE_XFIXES
++   // register for clipboard change notifications
++   if (have_xfixes && !win->parent()) {
++     XFixesSelectSelectionInput(fl_display, xp->xid, XA_PRIMARY,
++                                XFixesSetSelectionOwnerNotifyMask);
++     XFixesSelectSelectionInput(fl_display, xp->xid, CLIPBOARD,
++                                XFixesSetSelectionOwnerNotifyMask);
++   }
++ #endif
++ 
+    XMapWindow(fl_display, xp->xid);
+    if (showit) {
+***************
+*** 1798,1801 ****
+--- 2129,2138 ----
+      win->redraw();
+    }
++ 
++   // non-EWMH fullscreen case, need grab
++   if (win->flags() & Fl_Widget::FULLSCREEN && !ewmh_supported()) {
++     XGrabKeyboard(fl_display, xp->xid, 1, GrabModeAsync, GrabModeAsync, fl_event_time);
++   }
++ 
+  }
+  
+***************
+*** 1884,1887 ****
+--- 2221,2312 ----
+  ////////////////////////////////////////////////////////////////
+  
++ int Fl_X::set_cursor(Fl_Cursor c) {
++   unsigned int shape;
++   Cursor xc;
++ 
++   switch (c) {
++   case FL_CURSOR_ARROW:   shape = XC_left_ptr; break;
++   case FL_CURSOR_CROSS:   shape = XC_tcross; break;
++   case FL_CURSOR_WAIT:    shape = XC_watch; break;
++   case FL_CURSOR_INSERT:  shape = XC_xterm; break;
++   case FL_CURSOR_HAND:    shape = XC_hand2; break;
++   case FL_CURSOR_HELP:    shape = XC_question_arrow; break;
++   case FL_CURSOR_MOVE:    shape = XC_fleur; break;
++   case FL_CURSOR_NS:      shape = XC_sb_v_double_arrow; break;
++   case FL_CURSOR_WE:      shape = XC_sb_h_double_arrow; break;
++   case FL_CURSOR_NE:      shape = XC_top_right_corner; break;
++   case FL_CURSOR_N:       shape = XC_top_side; break;
++   case FL_CURSOR_NW:      shape = XC_top_left_corner; break;
++   case FL_CURSOR_E:       shape = XC_right_side; break;
++   case FL_CURSOR_W:       shape = XC_left_side; break;
++   case FL_CURSOR_SE:      shape = XC_bottom_right_corner; break;
++   case FL_CURSOR_S:       shape = XC_bottom_side; break;
++   case FL_CURSOR_SW:      shape = XC_bottom_left_corner; break;
++   default:
++     return 0;
++   }
++ 
++   xc = XCreateFontCursor(fl_display, shape);
++   XDefineCursor(fl_display, xid, xc);
++   XFreeCursor(fl_display, xc);
++ 
++   return 1;
++ }
++ 
++ int Fl_X::set_cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
++ #if ! HAVE_XCURSOR
++   return 0;
++ #else
++   XcursorImage *cursor;
++   Cursor xc;
++ 
++   if ((hotx < 0) || (hotx >= image->w()))
++     return 0;
++   if ((hoty < 0) || (hoty >= image->h()))
++     return 0;
++ 
++   cursor = XcursorImageCreate(image->w(), image->h());
++   if (!cursor)
++     return 0;
++ 
++   const uchar *i = (const uchar*)*image->data();
++   XcursorPixel *o = cursor->pixels;
++   for (int y = 0;y < image->h();y++) {
++     for (int x = 0;x < image->w();x++) {
++       switch (image->d()) {
++       case 1:
++         *o = (0xff<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
++         break;
++       case 2:
++         *o = (i[1]<<24) | (i[0]<<16) | (i[0]<<8) | i[0];
++         break;
++       case 3:
++         *o = (0xff<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
++         break;
++       case 4:
++         *o = (i[3]<<24) | (i[0]<<16) | (i[1]<<8) | i[2];
++         break;
++       }
++       i += image->d();
++       o++;
++     }
++     i += image->ld();
++   }
++ 
++   cursor->xhot = hotx;
++   cursor->yhot = hoty;
++ 
++   xc = XcursorImageLoadCursor(fl_display, cursor);
++   XDefineCursor(fl_display, xid, xc);
++   XFreeCursor(fl_display, xc);
++ 
++   XcursorImageDestroy(cursor);
++ 
++   return 1;
++ #endif
++ }
++ 
++ ////////////////////////////////////////////////////////////////
++ 
+  // returns pointer to the filename, or null if name ends with '/'
+  const char *fl_filename_name(const char *name) {
+*** fltk-1.3.0/src/fl_cursor.cxx	2010-12-18 16:31:01.000000000 -0600
+--- fltk-1.3.0.new/src/fl_cursor.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 34,331 ****
+  #include <FL/Fl.H>
+  #include <FL/Fl_Window.H>
+  #include <FL/x.H>
+- #if !defined(WIN32) && !defined(__APPLE__)
+- #  include <X11/cursorfont.h>
+- #endif
+  #include <FL/fl_draw.H>
+  
+  /**
+    Sets the cursor for the current window to the specified shape and colors.
+    The cursors are defined in the <FL/Enumerations.H> header file. 
+    */
+  void fl_cursor(Fl_Cursor c, Fl_Color fg, Fl_Color bg) {
+!   if (Fl::first_window()) Fl::first_window()->cursor(c,fg,bg);
+  }
+  /** 
+!     Sets the default window cursor as well as its color.
+  
+!     For back compatibility only.
+  */
+! void Fl_Window::default_cursor(Fl_Cursor c, Fl_Color fg, Fl_Color bg) {
+! //  if (c == FL_CURSOR_DEFAULT) c = FL_CURSOR_ARROW;
+! 
+    cursor_default = c;
+!   cursor_fg      = fg;
+!   cursor_bg      = bg;
+  
+!   cursor(c, fg, bg);
+  }
+  
+- #ifdef WIN32
+  
+! #  ifndef IDC_HAND
+! #    define IDC_HAND	MAKEINTRESOURCE(32649)
+! #  endif // !IDC_HAND
+  
+- void Fl_Window::cursor(Fl_Cursor c, Fl_Color c1, Fl_Color c2) {
+-   if (!shown()) return;
+    // the cursor must be set for the top level window, not for subwindows
+    Fl_Window *w = window(), *toplevel = this;
+!   while (w) { toplevel = w; w = w->window(); }
+!   if (toplevel != this) { toplevel->cursor(c, c1, c2); return; }
+!   // now set the actual cursor
+!   if (c == FL_CURSOR_DEFAULT) {
+!     c = cursor_default;
+!   }
+!   if (c > FL_CURSOR_NESW) {
+!     i->cursor = 0;
+!   } else if (c == FL_CURSOR_DEFAULT) {
+!     i->cursor = fl_default_cursor;
+!   } else {
+!     LPSTR n;
+!     switch (c) {
+!     case FL_CURSOR_ARROW:	n = IDC_ARROW; break;
+!     case FL_CURSOR_CROSS:	n = IDC_CROSS; break;
+!     case FL_CURSOR_WAIT:	n = IDC_WAIT; break;
+!     case FL_CURSOR_INSERT:	n = IDC_IBEAM; break;
+!     case FL_CURSOR_HELP:	n = IDC_HELP; break;
+!     case FL_CURSOR_HAND: {
+!           OSVERSIONINFO osvi;
+! 
+!           // Get the OS version: Windows 98 and 2000 have a standard
+! 	  // hand cursor.
+!           memset(&osvi, 0, sizeof(OSVERSIONINFO));
+!           osvi.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);
+!           GetVersionEx(&osvi);
+! 
+!           if (osvi.dwMajorVersion > 4 ||
+!   	      (osvi.dwMajorVersion == 4 && osvi.dwMinorVersion > 0 &&
+!   	       osvi.dwPlatformId == VER_PLATFORM_WIN32_WINDOWS)) n = IDC_HAND;
+!           else n = IDC_UPARROW;
+! 	} break;
+!     case FL_CURSOR_MOVE:	n = IDC_SIZEALL; break;
+!     case FL_CURSOR_N:
+!     case FL_CURSOR_S:
+!     case FL_CURSOR_NS:		n = IDC_SIZENS; break;
+!     case FL_CURSOR_NE:
+!     case FL_CURSOR_SW:
+!     case FL_CURSOR_NESW:	n = IDC_SIZENESW; break;
+!     case FL_CURSOR_E:
+!     case FL_CURSOR_W:
+!     case FL_CURSOR_WE:		n = IDC_SIZEWE; break;
+!     case FL_CURSOR_SE:
+!     case FL_CURSOR_NW:
+!     case FL_CURSOR_NWSE:	n = IDC_SIZENWSE; break;
+!     default:			n = IDC_NO; break;
+!     }
+!     i->cursor = LoadCursor(NULL, n);
+    }
+-   SetCursor(i->cursor);
+- }
+  
+! #elif defined(__APPLE__)
+  
+! #ifdef __BIG_ENDIAN__
+! # define E(x) x
+! #elif defined __LITTLE_ENDIAN__
+! // Don't worry. This will be resolved at compile time
+! # define E(x) (x>>8)|((x<<8)&0xff00)
+! #else
+! # error "Either __LITTLE_ENDIAN__ or __BIG_ENDIAN__ must be defined"
+! #endif
+! 
+! extern Fl_Offscreen fl_create_offscreen_with_alpha(int w, int h);
+! 
+! 
+! CGContextRef Fl_X::help_cursor_image(void)
+! {
+!   int w = 20, h = 20;
+!   Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
+!   fl_begin_offscreen(off);
+!   CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
+!   fl_rectf(0,0,w,h);
+!   fl_color(FL_BLACK);
+!   fl_font(FL_COURIER_BOLD, 20);
+!   fl_draw("?", 1, h-1);
+!   fl_end_offscreen();
+!   return (CGContextRef)off;
+! }
+  
+! CGContextRef Fl_X::none_cursor_image(void)
+! {
+!   int w = 20, h = 20;
+!   Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
+!   fl_begin_offscreen(off);
+!   CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
+!   fl_rectf(0,0,w,h);
+!   fl_end_offscreen();
+!   return (CGContextRef)off;
+! }
+  
+! CGContextRef Fl_X::watch_cursor_image(void)
+! {
+!   int w, h, r = 5;
+!   w = 2*r+6;
+!   h = 4*r;
+!   Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
+!   fl_begin_offscreen(off);
+!   CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
+!   fl_rectf(0,0,w,h);
+!   CGContextTranslateCTM( (CGContextRef)off, w/2, h/2);
+!   fl_color(FL_WHITE);
+!   fl_circle(0, 0, r+1);
+!   fl_color(FL_BLACK);
+!   fl_rectf(int(-r*0.7), int(-r*1.7), int(1.4*r), int(3.4*r));
+!   fl_rectf(r-1, -1, 3, 3);
+!   fl_color(FL_WHITE);
+!   fl_pie(-r, -r, 2*r, 2*r, 0, 360);
+!   fl_color(FL_BLACK);
+!   fl_circle(0,0,r);
+!   fl_xyline(0, 0, int(-r*.7));
+!   fl_xyline(0, 0, 0, int(-r*.7));
+!   fl_end_offscreen();
+!   return (CGContextRef)off;
+! }
+  
+! CGContextRef Fl_X::nesw_cursor_image(void)
+! {
+!   int c = 7, r = 2*c;
+!   int w = r, h = r;
+!   Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
+!   fl_begin_offscreen(off);
+!   CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
+!   fl_rectf(0,0,w,h);
+!   CGContextTranslateCTM( (CGContextRef)off, 0, h);
+!   CGContextScaleCTM( (CGContextRef)off, 1, -1);
+!   fl_color(FL_BLACK);
+!   fl_polygon(0, 0, c, 0, 0, c);
+!   fl_polygon(r, r, r, r-c, r-c, r);
+!   fl_line_style(FL_SOLID, 2, 0);
+!   fl_line(0,1, r,r+1);
+!   fl_line_style(FL_SOLID, 0, 0);
+!   fl_end_offscreen();
+!   return (CGContextRef)off;
+  }
+  
+! CGContextRef Fl_X::nwse_cursor_image(void)
+! {
+!   int c = 7, r = 2*c;
+!   int w = r, h = r;
+!   Fl_Offscreen off = fl_create_offscreen_with_alpha(w, h);
+!   fl_begin_offscreen(off);
+!   CGContextSetRGBFillColor( (CGContextRef)off, 0,0,0,0);
+!   fl_rectf(0,0,w,h);
+!   CGContextTranslateCTM( (CGContextRef)off, 0, h);
+!   CGContextScaleCTM( (CGContextRef)off, 1, -1);
+!   fl_color(FL_BLACK);
+!   fl_polygon(r-1, 0, r-1, c, r-1-c, 0);
+!   fl_polygon(-1, r, c-1, r, -1, r-c);
+!   fl_line_style(FL_SOLID, 2, 0);
+!   fl_line(r-1,1, -1,r+1);
+!   fl_line_style(FL_SOLID, 0, 0);
+!   fl_end_offscreen();
+!   return (CGContextRef)off;
+! }
+  
+! void Fl_Window::cursor(Fl_Cursor c, Fl_Color, Fl_Color) {
+!   if (c == FL_CURSOR_DEFAULT) {
+!     c = cursor_default;
+!   }
+!   if (i) i->set_cursor(c);
+! }
+  
+! #else
+  
+! // I like the MSWindows resize cursors, so I duplicate them here:
+  
+! #define CURSORSIZE 16
+! #define HOTXY 7
+! static struct TableEntry {
+!   uchar bits[CURSORSIZE*CURSORSIZE/8];
+!   uchar mask[CURSORSIZE*CURSORSIZE/8];
+!   Cursor cursor;
+! } table[] = {
+!   {{	// FL_CURSOR_NS
+!    0x00, 0x00, 0x80, 0x01, 0xc0, 0x03, 0xe0, 0x07, 0x80, 0x01, 0x80, 0x01,
+!    0x80, 0x01, 0x80, 0x01, 0x80, 0x01, 0x80, 0x01, 0x80, 0x01, 0x80, 0x01,
+!    0xe0, 0x07, 0xc0, 0x03, 0x80, 0x01, 0x00, 0x00},
+!    {
+!    0x80, 0x01, 0xc0, 0x03, 0xe0, 0x07, 0xf0, 0x0f, 0xf0, 0x0f, 0xc0, 0x03,
+!    0xc0, 0x03, 0xc0, 0x03, 0xc0, 0x03, 0xc0, 0x03, 0xc0, 0x03, 0xf0, 0x0f,
+!    0xf0, 0x0f, 0xe0, 0x07, 0xc0, 0x03, 0x80, 0x01}},
+!   {{	// FL_CURSOR_EW
+!    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x10,
+!    0x0c, 0x30, 0xfe, 0x7f, 0xfe, 0x7f, 0x0c, 0x30, 0x08, 0x10, 0x00, 0x00,
+!    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
+!    {
+!    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x18, 0x18, 0x1c, 0x38,
+!    0xfe, 0x7f, 0xff, 0xff, 0xff, 0xff, 0xfe, 0x7f, 0x1c, 0x38, 0x18, 0x18,
+!    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}},
+!   {{	// FL_CURSOR_NWSE
+!    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x78, 0x00, 0x38, 0x00, 0x78, 0x00,
+!    0xe8, 0x00, 0xc0, 0x01, 0x80, 0x03, 0x00, 0x17, 0x00, 0x1e, 0x00, 0x1c,
+!    0x00, 0x1e, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
+!    {
+!    0x00, 0x00, 0x00, 0x00, 0xfc, 0x00, 0xfc, 0x00, 0x7c, 0x00, 0xfc, 0x00,
+!    0xfc, 0x01, 0xec, 0x03, 0xc0, 0x37, 0x80, 0x3f, 0x00, 0x3f, 0x00, 0x3e,
+!    0x00, 0x3f, 0x00, 0x3f, 0x00, 0x00, 0x00, 0x00}},
+!   {{	// FL_CURSOR_NESW
+!    0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x1e, 0x00, 0x1c, 0x00, 0x1e,
+!    0x00, 0x17, 0x80, 0x03, 0xc0, 0x01, 0xe8, 0x00, 0x78, 0x00, 0x38, 0x00,
+!    0x78, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00},
+!    {
+!    0x00, 0x00, 0x00, 0x00, 0x00, 0x3f, 0x00, 0x3f, 0x00, 0x3e, 0x00, 0x3f,
+!    0x80, 0x3f, 0xc0, 0x37, 0xec, 0x03, 0xfc, 0x01, 0xfc, 0x00, 0x7c, 0x00,
+!    0xfc, 0x00, 0xfc, 0x00, 0x00, 0x00, 0x00, 0x00}},
+!   {{0}, {0}} // FL_CURSOR_NONE & unknown
+! };
+! 
+! void Fl_Window::cursor(Fl_Cursor c, Fl_Color fg, Fl_Color bg) {
+!   if (!shown()) return;
+!   Cursor xc;
+!   int deleteit = 0;
+!   if (c == FL_CURSOR_DEFAULT) {
+!     c  = cursor_default;
+!     fg = cursor_fg;
+!     bg = cursor_bg;
+    }
+  
+!   if (!c) {
+!     xc = None;
+!   } else {
+!     if (c >= FL_CURSOR_NS) {
+!       TableEntry *q = (c > FL_CURSOR_NESW) ? table+4 : table+(c-FL_CURSOR_NS);
+!       if (!(q->cursor)) {
+! 	XColor dummy = { 0 };
+! 	Pixmap p = XCreateBitmapFromData(fl_display,
+! 	  RootWindow(fl_display, fl_screen), (const char*)(q->bits),
+! 	  CURSORSIZE, CURSORSIZE);
+! 	Pixmap m = XCreateBitmapFromData(fl_display,
+! 	  RootWindow(fl_display, fl_screen), (const char*)(q->mask),
+! 	  CURSORSIZE, CURSORSIZE);
+! 	q->cursor = XCreatePixmapCursor(fl_display, p,m,&dummy, &dummy,
+! 					HOTXY, HOTXY);
+! 	XFreePixmap(fl_display, m);
+! 	XFreePixmap(fl_display, p);
+!       }
+!       xc = q->cursor;
+!     } else {
+!       xc = XCreateFontCursor(fl_display, (c-1)*2);
+!       deleteit = 1;
+!     }
+!     XColor fgc;
+!     uchar r,g,b;
+!     Fl::get_color(fg,r,g,b);
+!     fgc.red = r<<8; fgc.green = g<<8; fgc.blue = b<<8;
+!     XColor bgc;
+!     Fl::get_color(bg,r,g,b);
+!     bgc.red = r<<8; bgc.green = g<<8; bgc.blue = b<<8;
+!     XRecolorCursor(fl_display, xc, &fgc, &bgc);
+    }
+-   XDefineCursor(fl_display, fl_xid(this), xc);
+-   if (deleteit) XFreeCursor(fl_display, xc);
+- }
+  
+! #endif
+  
+  //
+--- 34,186 ----
+  #include <FL/Fl.H>
+  #include <FL/Fl_Window.H>
++ #include <FL/Fl_Pixmap.H>
++ #include <FL/Fl_RGB_Image.H>
+  #include <FL/x.H>
+  #include <FL/fl_draw.H>
+  
++ #include "fl_cursor_wait.xpm"
++ #include "fl_cursor_help.xpm"
++ #include "fl_cursor_nwse.xpm"
++ #include "fl_cursor_nesw.xpm"
++ #include "fl_cursor_none.xpm"
++ 
+  /**
+    Sets the cursor for the current window to the specified shape and colors.
+    The cursors are defined in the <FL/Enumerations.H> header file. 
+    */
++ void fl_cursor(Fl_Cursor c) {
++   if (Fl::first_window()) Fl::first_window()->cursor(c);
++ }
++ 
++ /* For back compatibility only. */
+  void fl_cursor(Fl_Cursor c, Fl_Color fg, Fl_Color bg) {
+!   fl_cursor(c);
+  }
++ 
++ 
+  /** 
+!     Sets the default window cursor. This is the cursor that will be used
+!     after the mouse pointer leaves a widget with a custom cursor set.
+  
+!     \see cursor(const Fl_RGB_Image*, int, int), default_cursor()
+  */
+! void Fl_Window::default_cursor(Fl_Cursor c) {
+    cursor_default = c;
+!   cursor(c);
+! }
+! 
+  
+! void fallback_cursor(Fl_Window *w, Fl_Cursor c) {
+!   const char **xpm;
+!   int hotx, hoty;
+! 
+!   // The standard arrow is our final fallback, so something is broken
+!   // if we get called back here with that as an argument.
+!   if (c == FL_CURSOR_ARROW)
+!     return;
+! 
+!   switch (c) {
+!   case FL_CURSOR_WAIT:
+!     xpm = (const char**)fl_cursor_wait_xpm;
+!     hotx = 8;
+!     hoty = 15;
+!     break;
+!   case FL_CURSOR_HELP:
+!     xpm = (const char**)fl_cursor_help_xpm;
+!     hotx = 1;
+!     hoty = 3;
+!     break;
+!   case FL_CURSOR_NWSE:
+!     xpm = (const char**)fl_cursor_nwse_xpm;
+!     hotx = 7;
+!     hoty = 7;
+!     break;
+!   case FL_CURSOR_NESW:
+!     xpm = (const char**)fl_cursor_nesw_xpm;
+!     hotx = 7;
+!     hoty = 7;
+!     break;
+!   case FL_CURSOR_NONE:
+!     xpm = (const char**)fl_cursor_none_xpm;
+!     hotx = 0;
+!     hoty = 0;
+!     break;
+!   default:
+!     w->cursor(FL_CURSOR_ARROW);
+!     return;
+!   }
+! 
+!   Fl_Pixmap pxm(xpm);
+!   Fl_RGB_Image image(&pxm);
+! 
+!   w->cursor(&image, hotx, hoty);
+  }
+  
+  
+! void Fl_Window::cursor(Fl_Cursor c) {
+!   int ret;
+  
+    // the cursor must be set for the top level window, not for subwindows
+    Fl_Window *w = window(), *toplevel = this;
+! 
+!   while (w) {
+!     toplevel = w;
+!     w = w->window();
+    }
+  
+!   if (toplevel != this) {
+!     toplevel->cursor(c);
+!     return;
+!   }
+  
+!   if (c == FL_CURSOR_DEFAULT)
+!     c = cursor_default;
+  
+!   if (!i)
+!     return;
+  
+!   ret = i->set_cursor(c);
+!   if (ret)
+!     return;
+  
+!   fallback_cursor(this, c);
+  }
+  
+! /**
+!   Changes the cursor for this window.  This always calls the system, if
+!   you are changing the cursor a lot you may want to keep track of how
+!   you set it in a static variable and call this only if the new cursor
+!   is different.
+  
+!   The default cursor will be used if the provided image cannot be used
+!   as a cursor.
+  
+!   \see cursor(Fl_Cursor), default_cursor()
+! */
+! void Fl_Window::cursor(const Fl_RGB_Image *image, int hotx, int hoty) {
+!   int ret;
+  
+!   // the cursor must be set for the top level window, not for subwindows
+!   Fl_Window *w = window(), *toplevel = this;
+  
+!   while (w) {
+!     toplevel = w;
+!     w = w->window();
+    }
+  
+!   if (toplevel != this) {
+!     toplevel->cursor(image, hotx, hoty);
+!     return;
+    }
+  
+!   if (!i)
+!     return;
+! 
+!   ret = i->set_cursor(image, hotx, hoty);
+!   if (ret)
+!     return;
+! 
+!   cursor(FL_CURSOR_DEFAULT);
+! }
+  
+  //
+*** fltk-1.3.0/src/fl_draw_pixmap.cxx	2011-02-02 12:39:34.000000000 -0600
+--- fltk-1.3.0.new/src/fl_draw_pixmap.cxx	2011-06-22 22:46:30.000000000 -0500
+***************
+*** 68,164 ****
+  }
+  
+- #ifdef U64
+- 
+- // The callback from fl_draw_image to get a row of data passes this:
+- struct pixmap_data {
+-   int w, h;
+-   const uchar*const* data;
+-   union {
+-     U64 colors[256];
+-     U64* byte1[256];
+-   };
+- };
+- 
+- // callback for 1 byte per pixel:
+- static void cb1(void*v, int x, int y, int w, uchar* buf) {
+-   pixmap_data& d = *(pixmap_data*)v;
+-   const uchar* p = d.data[y]+x;
+-   U64* q = (U64*)buf;
+-   for (int X=w; X>0; X-=2, p += 2) {
+-     if (X>1) {
+- #  if WORDS_BIGENDIAN
+-       *q++ = (d.colors[p[0]]<<32) | d.colors[p[1]];
+- #  else
+-       *q++ = (d.colors[p[1]]<<32) | d.colors[p[0]];
+- #  endif
+-     } else {
+- #  if WORDS_BIGENDIAN
+-       *q++ = d.colors[p[0]]<<32;
+- #  else
+-       *q++ = d.colors[p[0]];
+- #  endif
+-     }
+-   }
+- }
+- 
+- // callback for 2 bytes per pixel:
+- static void cb2(void*v, int x, int y, int w, uchar* buf) {
+-   pixmap_data& d = *(pixmap_data*)v;
+-   const uchar* p = d.data[y]+2*x;
+-   U64* q = (U64*)buf;
+-   for (int X=w; X>0; X-=2) {
+-     U64* colors = d.byte1[*p++];
+-     int index = *p++;
+-     if (X>1) {
+-       U64* colors1 = d.byte1[*p++];
+-       int index1 = *p++;
+- #  if WORDS_BIGENDIAN
+-       *q++ = (colors[index]<<32) | colors1[index1];
+- #  else
+-       *q++ = (colors1[index1]<<32) | colors[index];
+- #  endif
+-     } else {
+- #  if WORDS_BIGENDIAN
+-       *q++ = colors[index]<<32;
+- #  else
+-       *q++ = colors[index];
+- #  endif
+-     }
+-   }
+- }
+- 
+- #else // U32
+- 
+- // The callback from fl_draw_image to get a row of data passes this:
+- struct pixmap_data {
+-   int w, h;
+-   const uchar*const* data;
+-   union {
+-     U32 colors[256];
+-     U32* byte1[256];
+-   };
+- };
+- 
+- // callback for 1 byte per pixel:
+- static void cb1(void*v, int x, int y, int w, uchar* buf) {
+-   pixmap_data& d = *(pixmap_data*)v;
+-   const uchar* p = d.data[y]+x;
+-   U32* q = (U32*)buf;
+-   for (int X=w; X--;) *q++ = d.colors[*p++];
+- }
+- 
+- // callback for 2 bytes per pixel:
+- static void cb2(void*v, int x, int y, int w, uchar* buf) {
+-   pixmap_data& d = *(pixmap_data*)v;
+-   const uchar* p = d.data[y]+2*x;
+-   U32* q = (U32*)buf;
+-   for (int X=w; X--;) {
+-     U32* colors = d.byte1[*p++];
+-     *q++ = colors[*p++];
+-   }
+- }
+- 
+- #endif // U64 else U32
+- 
+  uchar **fl_mask_bitmap; // if non-zero, create bitmap and store pointer here
+  
+--- 68,71 ----
+***************
+*** 210,223 ****
+  #endif
+  
+! /**
+!   Draw XPM image data, with the top-left corner at the given position.
+!   \see fl_draw_pixmap(char* const* data, int x, int y, Fl_Color bg)
+!   */
+! int fl_draw_pixmap(const char*const* cdata, int x, int y, Fl_Color bg) {
+!   pixmap_data d;
+!   if (!fl_measure_pixmap(cdata, d.w, d.h)) return 0;
+    const uchar*const* data = (const uchar*const*)(cdata+1);
+    int transparent_index = -1;
+    uchar *transparent_c = (uchar *)0; // such that transparent_c[0,1,2] are the RGB of the transparent color
+  #ifdef WIN32
+    color_count = 0;
+--- 117,134 ----
+  #endif
+  
+! int fl_convert_pixmap(const char*const* cdata, uchar* out, Fl_Color bg) {
+!   int w, h;
+    const uchar*const* data = (const uchar*const*)(cdata+1);
+    int transparent_index = -1;
+    uchar *transparent_c = (uchar *)0; // such that transparent_c[0,1,2] are the RGB of the transparent color
++ 
++   if (!fl_measure_pixmap(cdata, w, h))
++     return 0;
++ 
++   if ((chars_per_pixel < 1) || (chars_per_pixel > 2))
++     return 0;
++ 
++   uchar (*colors)[4] = new uchar [1<<(chars_per_pixel*8)][4];
++ 
+  #ifdef WIN32
+    color_count = 0;
+***************
+*** 225,229 ****
+  #endif
+  
+!   if (ncolors < 0) {	// FLTK (non standard) compressed colormap
+      ncolors = -ncolors;
+      const uchar *p = *data++;
+--- 136,141 ----
+  #endif
+  
+!   if (ncolors < 0) {
+!     // FLTK (non standard) compressed colormap
+      ncolors = -ncolors;
+      const uchar *p = *data++;
+***************
+*** 231,241 ****
+      // it not be transparent):
+      if (*p == ' ') {
+!       uchar* c = (uchar*)&d.colors[(int)' '];
+! #ifdef U64
+!       *(U64*)c = 0;
+! #  if WORDS_BIGENDIAN
+!       c += 4;
+! #  endif
+! #endif
+        transparent_index = ' ';
+        Fl::get_color(bg, c[0], c[1], c[2]); c[3] = 0;
+--- 143,147 ----
+      // it not be transparent):
+      if (*p == ' ') {
+!       uchar* c = colors[(int)' '];
+        transparent_index = ' ';
+        Fl::get_color(bg, c[0], c[1], c[2]); c[3] = 0;
+***************
+*** 246,256 ****
+      // read all the rest of the colors:
+      for (int i=0; i < ncolors; i++) {
+!       uchar* c = (uchar*)&d.colors[*p++];
+! #ifdef U64
+!       *(U64*)c = 0;
+! #  if WORDS_BIGENDIAN
+!       c += 4;
+! #  endif
+! #endif
+  #ifdef WIN32
+        used_colors[3*color_count] = *p;
+--- 152,156 ----
+      // read all the rest of the colors:
+      for (int i=0; i < ncolors; i++) {
+!       uchar* c = colors[*p++];
+  #ifdef WIN32
+        used_colors[3*color_count] = *p;
+***************
+*** 262,273 ****
+        *c++ = *p++;
+        *c++ = *p++;
+- #ifdef __APPLE_QUARTZ__
+        *c = 255;
+- #else
+-       *c = 0;
+- #endif
+      }
+!   } else {	// normal XPM colormap with names
+!     if (chars_per_pixel>1) memset(d.byte1, 0, sizeof(d.byte1));
+      for (int i=0; i<ncolors; i++) {
+        const uchar *p = *data++;
+--- 162,169 ----
+        *c++ = *p++;
+        *c++ = *p++;
+        *c = 255;
+      }
+!   } else {
+!     // normal XPM colormap with names
+      for (int i=0; i<ncolors; i++) {
+        const uchar *p = *data++;
+***************
+*** 275,334 ****
+        int ind = *p++;
+        uchar* c;
+!       if (chars_per_pixel>1) {
+! #ifdef U64
+! 	U64* colors = d.byte1[ind];
+! 	if (!colors) colors = d.byte1[ind] = new U64[256];
+! #else
+! 	U32* colors = d.byte1[ind];
+! 	if (!colors) colors = d.byte1[ind] = new U32[256];
+! #endif
+! 	c = (uchar*)&colors[*p];
+! 	ind = (ind<<8)|*p++;
+!       } else {
+! 	c = (uchar *)&d.colors[ind];
+!       }
+        // look for "c word", or last word if none:
+        const uchar *previous_word = p;
+        for (;;) {
+! 	while (*p && isspace(*p)) p++;
+! 	uchar what = *p++;
+! 	while (*p && !isspace(*p)) p++;
+! 	while (*p && isspace(*p)) p++;
+! 	if (!*p) {p = previous_word; break;}
+! 	if (what == 'c') break;
+! 	previous_word = p;
+! 	while (*p && !isspace(*p)) p++;
+        }
+- #ifdef U64
+-       *(U64*)c = 0;
+- #  if WORDS_BIGENDIAN
+-       c += 4;
+- #  endif
+- #endif
+- #ifdef __APPLE_QUARTZ__
+-       c[3] = 255;
+- #endif
+        int parse = fl_parse_color((const char*)p, c[0], c[1], c[2]);
+        if (parse) {
+  #ifdef WIN32
+! 	used_colors[3*color_count] = c[0];
+! 	used_colors[3*color_count+1] = c[1];
+! 	used_colors[3*color_count+2] = c[2];
+! 	color_count++;
+  #endif
+! 	}
+!       else {
+          // assume "None" or "#transparent" for any errors
+! 	// "bg" should be transparent...
+! 	Fl::get_color(bg, c[0], c[1], c[2]);
+! #ifdef __APPLE_QUARTZ__
+          c[3] = 0;
+! #endif
+! 	transparent_index = ind;
+! 	transparent_c = c;
+        }
+      }
+    }
+-   d.data = data;
+  #ifdef WIN32
+    if (transparent_c) {
+--- 171,208 ----
+        int ind = *p++;
+        uchar* c;
+!       if (chars_per_pixel>1)
+!         ind = (ind<<8)|*p++;
+!       c = colors[ind];
+        // look for "c word", or last word if none:
+        const uchar *previous_word = p;
+        for (;;) {
+!         while (*p && isspace(*p)) p++;
+!         uchar what = *p++;
+!         while (*p && !isspace(*p)) p++;
+!         while (*p && isspace(*p)) p++;
+!         if (!*p) {p = previous_word; break;}
+!         if (what == 'c') break;
+!         previous_word = p;
+!         while (*p && !isspace(*p)) p++;
+        }
+        int parse = fl_parse_color((const char*)p, c[0], c[1], c[2]);
++       c[3] = 255;
+        if (parse) {
+  #ifdef WIN32
+!         used_colors[3*color_count] = c[0];
+!         used_colors[3*color_count+1] = c[1];
+!         used_colors[3*color_count+2] = c[2];
+!         color_count++;
+  #endif
+!       } else {
+          // assume "None" or "#transparent" for any errors
+!         // "bg" should be transparent...
+!         Fl::get_color(bg, c[0], c[1], c[2]);
+          c[3] = 0;
+!         transparent_index = ind;
+!         transparent_c = c;
+        }
+      }
+    }
+  #ifdef WIN32
+    if (transparent_c) {
+***************
+*** 340,425 ****
+    }
+  #endif
+    
+  #ifdef  __APPLE_QUARTZ__
+    if (fl_graphics_driver->class_name() == Fl_Quartz_Graphics_Driver::class_id ) {
+-     bool transparent = (transparent_index>=0);
+-     transparent = true;
+-     U32 *array = new U32[d.w * d.h], *q = array;
+-     for (int Y = 0; Y < d.h; Y++) {
+-       const uchar* p = data[Y];
+-       if (chars_per_pixel <= 1) {
+- 	for (int X = 0; X < d.w; X++) {
+- 	  *q++ = d.colors[*p++];
+- 	}
+-       } else {
+- 	for (int X = 0; X < d.w; X++) {
+- 	  U32* colors = (U32*)d.byte1[*p++];
+- 	  *q++ = colors[*p++];
+- 	}
+-       }
+-     }
+      CGColorSpaceRef lut = CGColorSpaceCreateDeviceRGB();
+!     CGDataProviderRef src = CGDataProviderCreateWithData( 0L, array, d.w * d.h * 4, 0L);
+!     CGImageRef img = CGImageCreate(d.w, d.h, 8, 4*8, 4*d.w,
+! 				   lut, transparent?kCGImageAlphaLast:kCGImageAlphaNoneSkipLast,
+! 				   src, 0L, false, kCGRenderingIntentDefault);
+      CGColorSpaceRelease(lut);
+      CGDataProviderRelease(src);
+!     CGRect rect = { { x, y} , { d.w, d.h } };
+!     Fl_X::q_begin_image(rect, 0, 0, d.w, d.h);
+      CGContextDrawImage(fl_gc, rect, img);
+      Fl_X::q_end_image();
+      CGImageRelease(img);
+!     delete[] array;
+!     }
+!   else {
+  #endif // __APPLE_QUARTZ__
+- 
+    // build the mask bitmap used by Fl_Pixmap:
+!   if (fl_mask_bitmap && transparent_index >= 0) {
+!     int W = (d.w+7)/8;
+!     uchar* bitmap = new uchar[W * d.h];
+      *fl_mask_bitmap = bitmap;
+!     for (int Y = 0; Y < d.h; Y++) {
+!       const uchar* p = data[Y];
+!       if (chars_per_pixel <= 1) {
+! 	int dw = d.w;
+! 	for (int X = 0; X < W; X++) {
+! 	  uchar b = (dw-->0 && *p++ != transparent_index);
+! 	  if (dw-->0 && *p++ != transparent_index) b |= 2;
+! 	  if (dw-->0 && *p++ != transparent_index) b |= 4;
+! 	  if (dw-->0 && *p++ != transparent_index) b |= 8;
+! 	  if (dw-->0 && *p++ != transparent_index) b |= 16;
+! 	  if (dw-->0 && *p++ != transparent_index) b |= 32;
+! 	  if (dw-->0 && *p++ != transparent_index) b |= 64;
+! 	  if (dw-->0 && *p++ != transparent_index) b |= 128;
+! 	  *bitmap++ = b;
+! 	}
+!       } else {
+!         uchar b = 0, bit = 1;
+! 	for (int X = 0; X < d.w; X++) {
+! 	  int ind = *p++;
+! 	  ind = (ind<<8) | (*p++);
+! 	  if (ind != transparent_index) b |= bit;
+! 
+!           if (bit < 128) bit <<= 1;
+! 	  else {
+! 	    *bitmap++ = b;
+! 	    b = 0;
+! 	    bit = 1;
+! 	  }
+! 	}
+! 
+!         if (bit > 1) *bitmap++ = b;
+        }
+      }
+    }
+  
+!   fl_draw_image(chars_per_pixel==1 ? cb1 : cb2, &d, x, y, d.w, d.h, 4);
+  #ifdef __APPLE_QUARTZ__
+      }
+  #endif
+  
+!   if (chars_per_pixel > 1) for (int i = 0; i < 256; i++) delete[] d.byte1[i];
+    return 1;
+  }
+--- 214,300 ----
+    }
+  #endif
++ 
++   U32 *q = (U32*)out;
++   for (int Y = 0; Y < h; Y++) {
++     const uchar* p = data[Y];
++     if (chars_per_pixel <= 1) {
++       for (int X = 0; X < w; X++)
++         memcpy(q++, colors[*p++], 4);
++     } else {
++       for (int X = 0; X < w; X++) {
++         int ind = (*p++)<<8;
++         ind |= *p++;
++         memcpy(q++, colors[ind], 4);
++       }
++     }
++   }
+    
++   delete [] colors;
++   return 1;
++ }
++ 
++ /**
++   Draw XPM image data, with the top-left corner at the given position.
++   \see fl_draw_pixmap(char* const* data, int x, int y, Fl_Color bg)
++   */
++ int fl_draw_pixmap(const char*const* cdata, int x, int y, Fl_Color bg) {
++   int w, h;
++ 
++   if (!fl_measure_pixmap(cdata, w, h))
++     return 0;
++ 
++   uchar *buffer = new uchar[w*h*4];
++ 
++   if (!fl_convert_pixmap(cdata, buffer, bg)) {
++     delete buffer;
++     return 0;
++   }
++ 
++   // FIXME: Hack until fl_draw_image() supports alpha properly
+  #ifdef  __APPLE_QUARTZ__
+    if (fl_graphics_driver->class_name() == Fl_Quartz_Graphics_Driver::class_id ) {
+      CGColorSpaceRef lut = CGColorSpaceCreateDeviceRGB();
+!     CGDataProviderRef src = CGDataProviderCreateWithData( 0L, buffer, w * h * 4, 0L);
+!     CGImageRef img = CGImageCreate(w, h, 8, 4*8, 4*w,
+!                                    lut, kCGImageAlphaLast,
+!                                    src, 0L, false, kCGRenderingIntentDefault);
+      CGColorSpaceRelease(lut);
+      CGDataProviderRelease(src);
+!     CGRect rect = { { x, y }, { w, h } };
+!     Fl_X::q_begin_image(rect, 0, 0, w, h);
+      CGContextDrawImage(fl_gc, rect, img);
+      Fl_X::q_end_image();
+      CGImageRelease(img);
+!   } else {
+  #endif // __APPLE_QUARTZ__
+    // build the mask bitmap used by Fl_Pixmap:
+!   if (fl_mask_bitmap) {
+!     int W = (w+7)/8;
+!     uchar* bitmap = new uchar[W * h];
+      *fl_mask_bitmap = bitmap;
+!     const uchar *p = &buffer[3];
+!     for (int Y = 0; Y < h; Y++) {
+!       int dw = w;
+!       for (int X = 0; X < W; X++) {
+!         uchar b = 0;
+!         for (int bit = 0x01;bit <= 0x80;bit<<=1) {
+!           if (dw-- < 0)
+!             break;
+!           if (*p > 127)
+!             b |= bit;
+!           p += 4;
+!         }
+!         *bitmap++ = b;
+        }
+      }
+    }
+  
+!   fl_draw_image(buffer, x, y, w, h, 4);
+! 
+  #ifdef __APPLE_QUARTZ__
+      }
+  #endif
+  
+!   delete buffer;
+    return 1;
+  }
+*** fltk-1.3.0/src/xutf8/imKStoUCS.c	2009-03-13 17:43:43.000000000 -0500
+--- fltk-1.3.0.new/src/xutf8/imKStoUCS.c	2011-06-22 22:35:31.000000000 -0500
+***************
+*** 267,270 ****
+--- 267,276 ----
+  };
+  
++ static unsigned short const keysym_to_unicode_fe50_fe60[] = {
++     0x0300, 0x0301, 0x0302, 0x0303, 0x0304, 0x0306, 0x0307, 0x0308, /* 0xfe50-0xfe57 */
++     0x030a, 0x030b, 0x030c, 0x0327, 0x0328, 0x1da5, 0x3099, 0x309a, /* 0xfe58-0xfe5f */
++     0x0323                                                          /* 0xfe60-0xfe67 */
++ };
++ 
+  unsigned int
+  KeySymToUcs4(KeySym keysym)
+***************
+*** 316,319 ****
+--- 322,327 ----
+      else if (keysym > 0x209f && keysym < 0x20ad)
+  	return keysym_to_unicode_20a0_20ac[keysym - 0x20a0];
++     else if (keysym > 0xfe4f && keysym < 0xfe61)
++ 	return keysym_to_unicode_fe50_fe60[keysym - 0xfe50];
+      else 
+  	return 0;
+*** fltk-1.3.0/test/cursor.cxx	2010-12-08 08:00:35.000000000 -0600
+--- fltk-1.3.0.new/test/cursor.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 33,38 ****
+  #include <FL/Fl_Box.H>
+  
+- Fl_Color fg = FL_BLACK;
+- Fl_Color bg = FL_WHITE;
+  Fl_Cursor cursor = FL_CURSOR_DEFAULT;
+  
+--- 33,36 ----
+***************
+*** 42,46 ****
+    cursor = (Fl_Cursor)(fl_intptr_t)v;
+    cursor_slider->value(cursor);
+!   fl_cursor(cursor,fg,bg);
+  }
+  
+--- 40,44 ----
+    cursor = (Fl_Cursor)(fl_intptr_t)v;
+    cursor_slider->value(cursor);
+!   fl_cursor(cursor);
+  }
+  
+***************
+*** 58,63 ****
+    {"FL_CURSOR_NWSE",0,choice_cb,(void*)FL_CURSOR_NWSE},
+    {"FL_CURSOR_NESW",0,choice_cb,(void*)FL_CURSOR_NESW},
+-   {"FL_CURSOR_NONE",0,choice_cb,(void*)FL_CURSOR_NONE},
+- #if 0
+    {"FL_CURSOR_N",0,choice_cb,(void*)FL_CURSOR_N},
+    {"FL_CURSOR_NE",0,choice_cb,(void*)FL_CURSOR_NE},
+--- 56,59 ----
+***************
+*** 68,72 ****
+    {"FL_CURSOR_W",0,choice_cb,(void*)FL_CURSOR_W},
+    {"FL_CURSOR_NW",0,choice_cb,(void*)FL_CURSOR_NW},
+! #endif
+    {0}
+  };
+--- 64,68 ----
+    {"FL_CURSOR_W",0,choice_cb,(void*)FL_CURSOR_W},
+    {"FL_CURSOR_NW",0,choice_cb,(void*)FL_CURSOR_NW},
+!   {"FL_CURSOR_NONE",0,choice_cb,(void*)FL_CURSOR_NONE},
+    {0}
+  };
+***************
+*** 75,91 ****
+    Fl_Hor_Value_Slider *slider = (Fl_Hor_Value_Slider *)o;
+    cursor = Fl_Cursor((int)slider->value());
+!   fl_cursor(cursor,fg,bg);
+! }
+! 
+! void setfg(Fl_Widget *o, void *) {
+!   Fl_Hor_Value_Slider *slider = (Fl_Hor_Value_Slider *)o;
+!   fg = Fl_Color((int)slider->value());
+!   fl_cursor(cursor,fg,bg);
+! }
+! 
+! void setbg(Fl_Widget *o, void *) {
+!   Fl_Hor_Value_Slider *slider = (Fl_Hor_Value_Slider *)o;
+!   bg = Fl_Color((int)slider->value());
+!   fl_cursor(cursor,fg,bg);
+  }
+  
+--- 71,75 ----
+    Fl_Hor_Value_Slider *slider = (Fl_Hor_Value_Slider *)o;
+    cursor = Fl_Cursor((int)slider->value());
+!   fl_cursor(cursor);
+  }
+  
+***************
+*** 113,139 ****
+    slider1.step(1);
+    slider1.precision(0);
+!   slider1.bounds(0,100);
+    slider1.value(0);
+    slider1.callback(setcursor);
+    slider1.value(cursor);
+  
+-   Fl_Hor_Value_Slider slider2(80,220,310,30,"fgcolor:");
+-   slider2.align(FL_ALIGN_LEFT);
+-   slider2.step(1);
+-   slider2.precision(0);
+-   slider2.bounds(0,255);
+-   slider2.value(0);
+-   slider2.callback(setfg);
+-   slider2.value(fg);
+- 
+-   Fl_Hor_Value_Slider slider3(80,260,310,30,"bgcolor:");
+-   slider3.align(FL_ALIGN_LEFT);
+-   slider3.step(1);
+-   slider3.precision(0);
+-   slider3.bounds(0,255);
+-   slider3.value(0);
+-   slider3.callback(setbg);
+-   slider3.value(bg);
+- 
+  #if 0
+    // draw the manual's diagram of cursors...
+--- 97,105 ----
+    slider1.step(1);
+    slider1.precision(0);
+!   slider1.bounds(0,255);
+    slider1.value(0);
+    slider1.callback(setcursor);
+    slider1.value(cursor);
+  
+  #if 0
+    // draw the manual's diagram of cursors...
+*** fltk-1.3.0/test/fullscreen.cxx	2010-12-15 06:11:16.000000000 -0600
+--- fltk-1.3.0.new/test/fullscreen.cxx	2011-06-22 22:35:32.000000000 -0500
+***************
+*** 61,66 ****
+--- 61,69 ----
+  #include <FL/Fl_Single_Window.H>
+  #include <FL/Fl_Hor_Slider.H>
++ #include <FL/Fl_Input.H>
++ #include <FL/Fl_Menu_Button.H>
+  #include <FL/Fl_Toggle_Light_Button.H>
+  #include <FL/math.h>
++ #include <FL/fl_ask.H>
+  #include <stdio.h>
+  
+***************
+*** 125,128 ****
+--- 128,153 ----
+  #endif
+  
++ class fullscreen_window : public Fl_Single_Window {
++ 
++   public:
++   fullscreen_window(int W, int H, const char *t=0);
++   int handle (int e);
++   Fl_Toggle_Light_Button *b3;
++ 
++ };
++ 
++ fullscreen_window::fullscreen_window(int W, int H, const char *t) : Fl_Single_Window(W, H, t) { 
++ 
++ }
++ 
++ int fullscreen_window::handle(int e) {
++   if (e == FL_FULLSCREEN) {
++     printf("Recieved FL_FULLSCREEN event\n");
++     b3->value(fullscreen_active());
++   }
++   if (Fl_Single_Window::handle(e)) return 1;
++   return 0;
++ }
++ 
+  void sides_cb(Fl_Widget *o, void *p) {
+    shape_window *sw = (shape_window *)p;
+***************
+*** 162,172 ****
+      pw = w->w();
+      ph = w->h();
+- #ifndef WIN32//necessary because fullscreen removes border
+- 	border_button->value(0);
+- 	border_button->do_callback();
+- #endif
+      w->fullscreen();
+    } else {
+!     w->fullscreen_off(px,py,pw,ph);
+    }
+  }
+--- 187,198 ----
+      pw = w->w();
+      ph = w->h();
+      w->fullscreen();
++     w->override();
++ #ifndef WIN32 // update our border state in case border was turned off
++     border_button->value(w->border());
++ #endif
+    } else {
+!     //w->fullscreen_off(px,py,pw,ph);
+!     w->fullscreen_off();
+    }
+  }
+***************
+*** 178,182 ****
+  }
+  
+! #define NUMB 5
+  
+  int twowindow = 0;
+--- 204,208 ----
+  }
+  
+! #define NUMB 6
+  
+  int twowindow = 0;
+***************
+*** 194,198 ****
+      Fl::fatal("Options are:\n -2 = 2 windows\n -f = startup fullscreen\n%s",Fl::help);
+  
+!   Fl_Single_Window window(300,300+30*NUMB); window.end();
+  
+    shape_window sw(10,10,window.w()-20,window.h()-30*NUMB-20);
+--- 220,224 ----
+      Fl::fatal("Options are:\n -2 = 2 windows\n -f = startup fullscreen\n%s",Fl::help);
+  
+!   fullscreen_window window(300,300+30*NUMB); window.end();
+  
+    shape_window sw(10,10,window.w()-20,window.h()-30*NUMB-20);
+***************
+*** 229,232 ****
+--- 255,261 ----
+    y+=30;
+  
++   Fl_Input i1(50,y,window.w()-60,30, "Input");
++   y+=30;
++ 
+    Fl_Toggle_Light_Button b2(50,y,window.w()-60,30,"Border");
+    b2.callback(border_cb,w);
+***************
+*** 235,240 ****
+    y+=30;
+  
+!   Fl_Toggle_Light_Button b3(50,y,window.w()-60,30,"FullScreen");
+!   b3.callback(fullscreen_cb,w);
+    y+=30;
+  
+--- 264,269 ----
+    y+=30;
+  
+!   window.b3 = new Fl_Toggle_Light_Button(50,y,window.w()-60,30,"FullScreen");
+!   window.b3->callback(fullscreen_cb,w);
+    y+=30;
+  
+***************
+*** 243,247 ****
+    y+=30;
+  
+!   if (initfull) {b3.set(); b3.do_callback();}
+  
+    window.end();
+--- 272,276 ----
+    y+=30;
+  
+!   if (initfull) {window.b3->set(); window.b3->do_callback();}
+  
+    window.end();
