XEmacs 21.4.20 "Double Solitaire".
[chise/xemacs-chise.git.1] / src / scrollbar-msw.c
index 2d7e9a9..8af6692 100644 (file)
@@ -41,6 +41,7 @@ Boston, MA 02111-1307, USA.  */
 #define VERTICAL_SCROLLBAR_DRAG_HACK
 
 static int vertical_drag_in_progress = 0;
+extern Lisp_Object mswindows_find_frame (HWND hwnd);
 
 static void
 mswindows_create_scrollbar_instance (struct frame *f, int vertical,
@@ -82,9 +83,11 @@ mswindows_create_scrollbar_instance (struct frame *f, int vertical,
 static void
 mswindows_free_scrollbar_instance (struct scrollbar_instance *sb)
 {
-  DestroyWindow (SCROLLBAR_MSW_HANDLE (sb));
   if (sb->scrollbar_data)
-    xfree (sb->scrollbar_data);
+    {
+      DestroyWindow (SCROLLBAR_MSW_HANDLE (sb));
+      xfree (sb->scrollbar_data);
+    }
 }
 
 static void
@@ -203,23 +206,36 @@ mswindows_handle_scrollbar_event (HWND hwnd, int code, int pos)
   }
 
   sb = (struct scrollbar_instance *)GetWindowLong (hwnd, GWL_USERDATA);
-  win = real_window ((sb==NULL) ? GetFocus() : sb->mirror, 1);
-  /* "0 as the second parameter" refers to the call to real_window above.
-     This comment was taken from Ben's 21.5 code that differs somewhat
-     from this, I don't think the 21.4 code ever had a 0 there.
-     #### we're still hitting an abort here with 0 as the second
-     parameter, although only occasionally.  It seems that sometimes we
-     receive events for scrollbars that don't exist anymore.  I assume
-     it must happen like this: The user does something that causes a
-     scrollbar to disappear (e.g. Alt-TAB, causing recomputation of
-     everything in the new frame) and then immediately uses the mouse
-     wheel, generating scrollbar events.  Both events get posted before
-     we have a chance to process them, and in processing the first, the
-     scrollbar mentioned in the second disappears. */
-  if (NILP (win))
-    return;
-  frame = XWINDOW (win)->frame;
-  f = XFRAME (frame);
+  if (sb != NULL) 
+    {
+      win = real_window (sb->mirror, 1);
+      /* "0 as the second parameter" refers to the call to real_window
+     above.  This comment was taken from Ben's 21.5 code that differs
+     somewhat from this, I don't think the 21.4 code ever had a 0
+     there.  #### we're still hitting an ABORT here with 0 as the
+     second parameter, although only occasionally.  It seems that
+     sometimes we receive events for scrollbars that don't exist
+     anymore.  I assume it must happen like this: The user does
+     something that causes a scrollbar to disappear (e.g. Alt-TAB,
+     causing recomputation of everything in the new frame) and then
+     immediately uses the mouse wheel, generating scrollbar events.
+     Both events get posted before we have a chance to process them,
+     and in processing the first, the scrollbar mentioned in the
+     second disappears. */
+      if (NILP (win))
+       return;
+      frame = XWINDOW (win)->frame;
+      f = XFRAME (frame);
+    }
+  else 
+    {
+      /* I'm not sure if this is right, but its much better than
+        passing an HNWD to real_window() - which is what the previous
+        code did -- andyp */
+      frame = mswindows_find_frame (GetFocus());
+      f = XFRAME (frame);
+      win = FRAME_SELECTED_WINDOW (f);
+    }
 
   /* SB_LINEDOWN == SB_CHARLEFT etc. This is the way they will
      always be - any Windows is binary compatible backward with
@@ -319,43 +335,45 @@ mswindows_handle_mousewheel_event (Lisp_Object frame, int keys, int delta,
 {
   int hasVertBar, hasHorzBar;  /* Indicates presence of scroll bars */
   unsigned wheelScrollLines = 0; /* Number of lines per wheel notch */
-  Lisp_Object win;
+  Lisp_Object win, corpore, sano;
   struct window_mirror *mirror;
+  int mene, _mene, tekel, upharsin;
+  Bufpos mens, sana;
+  Charcount in;
+  struct window *needle_in_haystack = 0;
   POINT donde_esta;
 
   donde_esta.x = where.x;
   donde_esta.y = where.y;
 
-  ScreenToClient (FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), &donde_esta);
-
   /* Find the window to scroll */
-  {
-    int mene, _mene, tekel, upharsin;
-    Bufpos mens, sana;
-    Charcount in;
-    Lisp_Object corpore, sano;
-    struct window *needle_in_haystack;
-
-    // stderr_out ("donde_esta: %d %d\n", donde_esta.x, donde_esta.y);
-    pixel_to_glyph_translation (XFRAME (frame), donde_esta.x, donde_esta.y,
-                               &mene, &_mene, &tekel, &upharsin,
-                               &needle_in_haystack,
-                               &mens, &sana, &in, &corpore, &sano);
-
-    if (needle_in_haystack)
-      {
-       XSETWINDOW (win, needle_in_haystack);
-       // stderr_out ("found needle\n");
-       // debug_print (win);
-      }
-    else
-      {
-       win = FRAME_SELECTED_WINDOW (XFRAME (frame));
-       needle_in_haystack = XWINDOW (win);
-      }
 
-    mirror = find_window_mirror (needle_in_haystack);
-  }
+  /* The mouse event could actually occur outside of the emacs
+     frame. */
+  if (ScreenToClient (FRAME_MSWINDOWS_HANDLE (XFRAME (frame)), 
+                     &donde_esta) != 0)
+    {
+      /* stderr_out ("donde_esta: %d %d\n", donde_esta.x, donde_esta.y); */
+      pixel_to_glyph_translation (XFRAME (frame), donde_esta.x, donde_esta.y,
+                                 &mene, &_mene, &tekel, &upharsin,
+                                 &needle_in_haystack,
+                                 &mens, &sana, &in, &corpore, &sano);
+      
+      if (needle_in_haystack)
+       {
+         XSETWINDOW (win, needle_in_haystack);
+         /* stderr_out ("found needle\n");
+            debug_print (win); */
+       }
+    }
+  
+  if (!needle_in_haystack)
+    {
+      win = FRAME_SELECTED_WINDOW (XFRAME (frame));
+      needle_in_haystack = XWINDOW (win);
+    }
+
+  mirror = find_window_mirror (needle_in_haystack);
 
   /* Check that there is something to scroll */
   hasVertBar = can_scroll (mirror->scrollbar_vertical_instance);