]> code.delx.au - gnu-emacs/blobdiff - lwlib/xlwmenu.c
Merge from emacs--devo--0
[gnu-emacs] / lwlib / xlwmenu.c
index b128e6cefb1682f0565a092ab94ba7ba8ee8b0df..77cc50e9d7ac1acd6e3e47928c61f8d683019332 100644 (file)
@@ -1,6 +1,6 @@
 /* Implements a lightweight menubar widget.
    Copyright (C) 1992 Lucid, Inc.
-   Copyright (C) 2002, 2005 Free Software Foundation, Inc.
+   Copyright (C) 2002, 2003, 2004, 2005, 2006 Free Software Foundation, Inc.
 
 This file is part of the Lucid Widget Library.
 
@@ -16,8 +16,8 @@ GNU General Public License for more details.
 
 You should have received a copy of the GNU General Public License
 along with GNU Emacs; see the file COPYING.  If not, write to the
-Free Software Foundation, Inc., 59 Temple Place - Suite 330,
-Boston, MA 02111-1307, USA.  */
+Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+Boston, MA 02110-1301, USA.  */
 
 /* Created by devin@lucid.com */
 
@@ -53,21 +53,8 @@ extern int gray_bitmap_width;
 extern int gray_bitmap_height;
 extern char *gray_bitmap_bits;
 
-/* Defined in xterm.c.  */
-extern int x_alloc_nearest_color_for_widget __P ((Widget, Colormap, XColor*));
-extern int x_alloc_lighter_color_for_widget __P ((Widget, Display*, Colormap,
-                                                 unsigned long *,
-                                                 double, int));
-extern int x_catch_errors __P ((Display*));
-extern int x_uncatch_errors __P ((Display*, int));
-extern int x_had_errors_p __P ((Display*));
-extern int x_clear_errors __P ((Display*));
-extern unsigned long x_copy_dpy_color __P ((Display *, Colormap,
-                                           unsigned long));
-
-/* Defined in xfaces.c.  */
-extern void x_free_dpy_colors __P ((Display *, Screen *, Colormap,
-                                   unsigned long *pixels, int npixels));
+#include "xterm.h"
+
 #else /* not emacs */
 
 #include <X11/bitmaps/gray>
@@ -136,12 +123,11 @@ static XtResource
 xlwMenuResources[] =
 {
 #ifdef HAVE_X_I18N
-  {XtNfont,  XtCFont, XtRFontSet, sizeof(XFontSet),
-     offset(menu.font), XtRString, "XtDefaultFontSet"},
-#else
+  {XtNfontSet,  XtCFontSet, XtRFontSet, sizeof(XFontSet),
+     offset(menu.fontSet), XtRFontSet, NULL},
+#endif
   {XtNfont,  XtCFont, XtRFontStruct, sizeof(XFontStruct *),
      offset(menu.font), XtRString, "XtDefaultFont"},
-#endif
   {XtNforeground, XtCForeground, XtRPixel, sizeof(Pixel),
      offset(menu.foreground), XtRString, "XtDefaultForeground"},
   {XtNdisabledForeground, XtCDisabledForeground, XtRPixel, sizeof(Pixel),
@@ -353,29 +339,36 @@ make_old_stack_space (mw, n)
 }
 
 \f/* Size code */
-int
+static int
 string_width (mw, s)
      XlwMenuWidget mw;
      char *s;
 {
-#ifdef HAVE_X_I18N
-  XRectangle ink, logical;
-  XmbTextExtents (mw->menu.font, s, strlen (s), &ink, &logical);
-  return logical.width;
-#else
   XCharStruct xcs;
   int drop;
+#ifdef HAVE_X_I18N
+  XRectangle ink, logical;
+  if (mw->menu.fontSet)
+    {
+      XmbTextExtents (mw->menu.fontSet, s, strlen (s), &ink, &logical);
+      return logical.width;
+    }
+#endif
 
   XTextExtents (mw->menu.font, s, strlen (s), &drop, &drop, &drop, &xcs);
   return xcs.width;
-#endif
+
 }
 
 #ifdef HAVE_X_I18N
 #define MENU_FONT_HEIGHT(mw) \
-  ((mw)->menu.font_extents->max_logical_extent.height)
+  ((mw)->menu.fontSet != NULL \
+   ? (mw)->menu.font_extents->max_logical_extent.height   \
+   : (mw)->menu.font->ascent + (mw)->menu.font->descent)
 #define MENU_FONT_ASCENT(mw) \
-  (- (mw)->menu.font_extents->max_logical_extent.y)
+  ((mw)->menu.fontSet != NULL \
+   ? - (mw)->menu.font_extents->max_logical_extent.y \
+   : (mw)->menu.font->ascent)
 #else
 #define MENU_FONT_HEIGHT(mw) \
   ((mw)->menu.font->ascent + (mw)->menu.font->descent)
@@ -1050,10 +1043,14 @@ display_menu_item (mw, val, ws, where, highlighted_p, horizontal_p,
 
 
 #ifdef HAVE_X_I18N
-          XmbDrawString (XtDisplay (mw), ws->window, mw->menu.font,
-#else
-          XDrawString (XtDisplay (mw), ws->window,
+          if (mw->menu.fontSet)
+            XmbDrawString (XtDisplay (mw), ws->window, mw->menu.fontSet,
+                           text_gc, x_offset,
+                           y + v_spacing + shadow + font_ascent,
+                           display_string, strlen (display_string));
+          else
 #endif
+          XDrawString (XtDisplay (mw), ws->window,
                       text_gc, x_offset,
                       y + v_spacing + shadow + font_ascent,
                       display_string, strlen (display_string));
@@ -1080,10 +1077,16 @@ display_menu_item (mw, val, ws, where, highlighted_p, horizontal_p,
              else if (val->key)
                {
 #ifdef HAVE_X_I18N
-                 XmbDrawString (XtDisplay (mw), ws->window, mw->menu.font,
-#else
-                 XDrawString (XtDisplay (mw), ws->window,
+                  if (mw->menu.fontSet)
+                    XmbDrawString (XtDisplay (mw), ws->window,
+                                   mw->menu.fontSet,
+                                   text_gc,
+                                   x + label_width + mw->menu.arrow_spacing,
+                                   y + v_spacing + shadow + font_ascent,
+                                   val->key, strlen (val->key));
+                  else
 #endif
+                 XDrawString (XtDisplay (mw), ws->window,
                               text_gc,
                               x + label_width + mw->menu.arrow_spacing,
                               y + v_spacing + shadow + font_ascent,
@@ -1490,34 +1493,25 @@ make_drawing_gcs (mw)
 {
   XGCValues xgcv;
   float scale;
+  XtGCMask mask = GCForeground | GCBackground;
 
-#ifndef HAVE_X_I18N
+#ifdef HAVE_X_I18N
+  if (!mw->menu.fontSet)
+    {
+      xgcv.font = mw->menu.font->fid;
+      mask |= GCFont;
+    }
+#else
   xgcv.font = mw->menu.font->fid;
+  mask |= GCFont;
 #endif
   xgcv.foreground = mw->menu.foreground;
   xgcv.background = mw->core.background_pixel;
-  mw->menu.foreground_gc = XtGetGC ((Widget)mw,
-#ifndef HAVE_X_I18N
-                                   GCFont |
-#endif
-                                   GCForeground | GCBackground,
-                                   &xgcv);
+  mw->menu.foreground_gc = XtGetGC ((Widget)mw, mask, &xgcv);
 
-#ifndef HAVE_X_I18N
-  xgcv.font = mw->menu.font->fid;
-#endif
   xgcv.foreground = mw->menu.button_foreground;
-  xgcv.background = mw->core.background_pixel;
-  mw->menu.button_gc = XtGetGC ((Widget)mw,
-#ifndef HAVE_X_I18N
-                               GCFont |
-#endif
-                               GCForeground | GCBackground,
-                               &xgcv);
+  mw->menu.button_gc = XtGetGC ((Widget)mw, mask, &xgcv);
 
-#ifndef HAVE_X_I18N
-  xgcv.font = mw->menu.font->fid;
-#endif
   xgcv.background = mw->core.background_pixel;
 
 #define BRIGHTNESS(color) (((color) & 0xff) + (((color) >> 8) & 0xff) + (((color) >> 16) & 0xff))
@@ -1542,49 +1536,26 @@ make_drawing_gcs (mw)
       xgcv.foreground = mw->menu.foreground;
       xgcv.fill_style = FillStippled;
       xgcv.stipple = mw->menu.gray_pixmap;
-      mw->menu.disabled_gc = XtGetGC ((Widget)mw,
-#ifndef HAVE_X_I18N
-                                     GCFont |
-#endif
-                                     GCForeground | GCBackground
+      mw->menu.disabled_gc = XtGetGC ((Widget)mw, mask
                                      | GCFillStyle | GCStipple, &xgcv);
     }
   else
     {
       /* Many colors available, use disabled pixel.  */
       xgcv.foreground = mw->menu.disabled_foreground;
-      mw->menu.disabled_gc = XtGetGC ((Widget)mw,
-#ifndef HAVE_X_I18N
-                                     GCFont |
-#endif
-                                     GCForeground | GCBackground, &xgcv);
+      mw->menu.disabled_gc = XtGetGC ((Widget)mw, mask, &xgcv);
     }
 
-#ifndef HAVE_X_I18N
-  xgcv.font = mw->menu.font->fid;
-#endif
   xgcv.foreground = mw->menu.button_foreground;
   xgcv.background = mw->core.background_pixel;
   xgcv.fill_style = FillStippled;
   xgcv.stipple = mw->menu.gray_pixmap;
-  mw->menu.inactive_button_gc = XtGetGC ((Widget)mw,
-#ifndef HAVE_X_I18N
-                                        GCFont |
-#endif
-                                        GCForeground | GCBackground
+  mw->menu.inactive_button_gc = XtGetGC ((Widget)mw, mask
                                         | GCFillStyle | GCStipple, &xgcv);
 
-#ifndef HAVE_X_I18N
-  xgcv.font = mw->menu.font->fid;
-#endif
   xgcv.foreground = mw->core.background_pixel;
   xgcv.background = mw->menu.foreground;
-  mw->menu.background_gc = XtGetGC ((Widget)mw,
-#ifndef HAVE_X_I18N
-                                   GCFont |
-#endif
-                                   GCForeground | GCBackground,
-                                   &xgcv);
+  mw->menu.background_gc = XtGetGC ((Widget)mw, mask, &xgcv);
 }
 
 static void
@@ -1790,14 +1761,14 @@ XlwMenuInitialize (request, mw, args, num_args)
                                   gray_bitmap_width, gray_bitmap_height,
                                   (unsigned long)1, (unsigned long)0, 1);
 
-#ifndef HAVE_X_I18N
   /* I don't understand why this ends up 0 sometimes,
      but it does.  This kludge works around it.
      Can anyone find a real fix?   -- rms.  */
   if (mw->menu.font == 0)
     mw->menu.font = xlwmenu_default_font;
-#else
-  mw->menu.font_extents = XExtentsOfFontSet (mw->menu.font);
+#ifdef HAVE_X_I18N
+  if (mw->menu.fontSet)
+    mw->menu.font_extents = XExtentsOfFontSet (mw->menu.fontSet);
 #endif
       
   make_drawing_gcs (mw);
@@ -1966,7 +1937,10 @@ XlwMenuSetValues (current, request, new)
 
   if (newmw->core.background_pixel != oldmw->core.background_pixel
       || newmw->menu.foreground != oldmw->menu.foreground
-#ifndef HAVE_X_I18N
+#ifdef HAVE_X_I18N
+      || newmw->menu.fontSet != oldmw->menu.fontSet
+      || (newmw->menu.fontSet == NULL && newmw->menu.font != oldmw->menu.font)
+#else
       || newmw->menu.font != oldmw->menu.font
 #endif
       )
@@ -1996,10 +1970,10 @@ XlwMenuSetValues (current, request, new)
     }
 
 #ifdef HAVE_X_I18N
-  if (newmw->menu.font != oldmw->menu.font)
+  if (newmw->menu.fontSet != oldmw->menu.fontSet && newmw->menu.fontSet != NULL)
     {
       redisplay = True;
-      newmw->menu.font_extents = XExtentsOfFontSet (newmw->menu.font);
+      newmw->menu.font_extents = XExtentsOfFontSet (newmw->menu.fontSet);
     }
 #endif
 
@@ -2101,6 +2075,7 @@ Start (w, ev, params, num_params)
       mw->menu.windows [0].y = ev->xmotion.y_root - ev->xmotion.y;
 
       /* handles the down like a move, slots are compatible */
+      ev->xmotion.is_hint = 0;
       handle_motion_event (mw, &ev->xmotion);
     }
 }
@@ -2151,6 +2126,7 @@ static widget_value *
 find_next_selectable (mw, item, skip_titles)
      XlwMenuWidget mw;
      widget_value *item;
+     int skip_titles;
 {
   widget_value *current = item;
   enum menu_separator separator;
@@ -2187,6 +2163,7 @@ static widget_value *
 find_prev_selectable (mw, item, skip_titles)
      XlwMenuWidget mw;
      widget_value *item;
+     int skip_titles;
 {
   widget_value *current = item;
   widget_value *prev = item;
@@ -2436,7 +2413,6 @@ pop_up_menu (mw, event)
   int          borderwidth = mw->menu.shadow_thickness;
   Screen*      screen = XtScreen (mw);
   Display       *display = XtDisplay (mw);
-  int count;
 
   next_release_must_exit = 0;
 
@@ -2483,7 +2459,7 @@ pop_up_menu (mw, event)
     }
 
 #ifdef emacs
-  count = x_catch_errors (display);
+  x_catch_errors (display);
 #endif
   if (XtGrabPointer ((Widget)mw, False,
                      (PointerMotionMask
@@ -2511,9 +2487,10 @@ pop_up_menu (mw, event)
       pointer_grabbed = 0;
       XtUngrabPointer ((Widget)mw, event->time);
     }
-  x_uncatch_errors (display, count);
+  x_uncatch_errors ();
 #endif
 
+  ((XMotionEvent*)event)->is_hint = 0;
   handle_motion_event (mw, (XMotionEvent*)event);
 }