Cancel previous changes
authorhanda <handa>
Tue, 6 Jul 2004 11:36:45 +0000 (11:36 +0000)
committerhanda <handa>
Tue, 6 Jul 2004 11:36:45 +0000 (11:36 +0000)
src/m17n-X.c
src/m17n-X.h
src/m17n-gd.c
src/m17n-gui.c
src/m17n-gui.h

index 28a6c0e..ef46273 100644 (file)
@@ -842,9 +842,9 @@ static void xft_render (MDrawWindow, int, int, MGlyphString *,
                        MGlyph *, MGlyph *, int, MDrawRegion);
 
 MFontDriver xft_driver =
-  { NULL,                      /* Set to ft_select in mwin__init (). */
+  { NULL,                      /* Set to ft_select in device_init (). */
     xft_open, xft_find_metric,
-    NULL,                      /* Set to ft_encode_char in mwin__init (). */
+    NULL,                      /* Set to ft_encode_char in device_init (). */
     xft_render };
 
 
@@ -999,272 +999,6 @@ xft_render (MDrawWindow win, int x, int y,
 \f
 /* Functions for the device driver.  */
 
-static int
-mwin__device_init ()
-{
-  M_iso8859_1 = msymbol ("iso8859-1");
-  M_iso10646_1 = msymbol ("iso10646-1");
-
-  display_info_list = mplist ();
-  device_list = mplist ();
-
-  Mxim = msymbol ("xim");
-  msymbol_put (Mxim, Minput_driver, &minput_xim_driver);
-
-  return 0;
-}
-
-static int
-mwin__device_fini ()
-{
-  M17N_OBJECT_UNREF (display_info_list);
-  M17N_OBJECT_UNREF (device_list);
-  return 0;
-}
-
-/** Return an MWDevice object corresponding to a display specified in
-    PLIST.
-
-    It searches device_list for a device matching the display.  If
-    found, return the found object.  Otherwise, return a newly created
-    object.  */
-
-static int
-mwin__open_device (MFrame *frame, MPlist *param)
-{
-  Display *display = NULL;
-  Screen *screen = NULL;
-  int screen_num;
-  Drawable drawable = 0;
-  Widget widget = NULL;
-  Colormap cmap = 0;
-  int auto_display = 0;
-  MDisplayInfo *disp_info = NULL;
-  MWDevice *device = NULL;
-  MSymbol key;
-  XWindowAttributes attr;
-  unsigned depth = 0;
-  MPlist *plist;
-  AppData app_data;
-  MFace *face;
-
-  for (plist = param; (key = mplist_key (plist)) != Mnil;
-       plist = mplist_next (plist))
-    {
-      if (key == Mdisplay)
-       display = (Display *) mplist_value (plist);
-      else if (key == Mscreen)
-       screen = mplist_value (plist);
-      else if (key == Mdrawable)
-       drawable = (Drawable) mplist_value (plist);
-      else if (key == Mdepth)
-       depth = (unsigned) mplist_value (plist);
-      else if (key == Mwidget)
-       widget = (Widget) mplist_value (plist);
-      else if (key == Mcolormap)
-       cmap = (Colormap) mplist_value (plist);
-    }
-
-  if (widget)
-    {
-      display = XtDisplay (widget);
-      screen_num = XScreenNumberOfScreen (XtScreen (widget));
-      depth = DefaultDepth (display, screen_num);
-    }
-  else if (drawable)
-    {
-      Window root_window;
-      int x, y;
-      unsigned width, height, border_width;
-
-      if (! display)
-       MERROR (MERROR_WIN, -1);
-      XGetGeometry (display, drawable, &root_window,
-                   &x, &y, &width, &height, &border_width, &depth);
-      XGetWindowAttributes (display, root_window, &attr);
-      screen_num = XScreenNumberOfScreen (attr.screen);
-    }
-  else
-    {
-      if (screen)
-       display = DisplayOfScreen (screen);
-      else
-       {
-         if (! display)
-           {
-             display = XOpenDisplay (NULL);
-             if (! display)
-               MERROR (MERROR_WIN, -1);
-             auto_display = 1;
-           }
-         screen = DefaultScreenOfDisplay (display);
-       }
-      screen_num = XScreenNumberOfScreen (screen);
-      if (! depth)
-       depth = DefaultDepth (display, screen_num);
-    }
-
-  if (! cmap)
-    cmap = DefaultColormap (display, screen_num);
-
-  for (plist = display_info_list; mplist_key (plist) != Mnil;
-       plist = mplist_next (plist))
-    {
-      disp_info = (MDisplayInfo *) mplist_value (plist);
-      if (disp_info->display == display)
-       break;
-    }
-
-  if (mplist_key (plist) != Mnil)
-    M17N_OBJECT_REF (disp_info);
-  else
-    {
-      M17N_OBJECT (disp_info, free_display_info, MERROR_WIN);
-      disp_info->display = display;
-      disp_info->auto_display = auto_display;
-      disp_info->font_registry_list = mplist ();
-      disp_info->iso8859_1_family_list = mplist ();
-      disp_info->iso10646_1_family_list = mplist ();
-      disp_info->realized_font_list = mplist ();
-      find_modifier_bits (disp_info);
-      mplist_add (display_info_list, Mt, disp_info);
-    }  
-
-  for (plist = device_list; mplist_key (plist) != Mnil;
-       plist = mplist_next (plist))
-    {
-      device = (MWDevice *) mplist_value (plist);
-      if (device->display_info == disp_info
-         && device->depth == depth
-         && device->cmap == cmap)
-       break;
-    }
-
-  if (mplist_key (plist) != Mnil)
-    M17N_OBJECT_REF (device);
-  else
-    {
-      unsigned long valuemask = GCForeground;
-      XGCValues values;
-
-      M17N_OBJECT (device, free_device, MERROR_WIN);
-      device->display_info = disp_info;
-      device->screen_num = screen_num;
-      /* A drawable on which to create GCs.  */
-      device->drawable = XCreatePixmap (display,
-                                       RootWindow (display, screen_num),
-                                       1, 1, depth);
-      device->depth = depth;
-      device->cmap = cmap;
-      device->realized_face_list = mplist ();
-      device->realized_fontset_list = mplist ();
-      device->gc_list = mplist ();
-      values.foreground = BlackPixel (display, screen_num);
-      device->scratch_gc = XCreateGC (display, device->drawable,
-                                     valuemask, &values);
-#ifdef HAVE_XFT2
-      device->xft_draw = XftDrawCreate (display, device->drawable,
-                                       DefaultVisual (display, screen_num),
-                                       cmap);
-#endif
-    }
-
-  frame->device = device;
-  frame->device_type = MDEVICE_SUPPORT_OUTPUT | MDEVICE_SUPPORT_INPUT;
-  frame->font_driver_list = mplist ();
-  mplist_add (frame->font_driver_list, Mx, &xfont_driver);
-#ifdef HAVE_XFT2
-  mplist_add (frame->font_driver_list, Mfreetype, &xft_driver);
-#elif HAVE_FREETYPE
-  mplist_add (frame->font_driver_list, Mfreetype, &mfont__ft_driver);
-#endif
-  frame->realized_font_list = disp_info->realized_font_list;
-  frame->realized_face_list = device->realized_face_list;
-  frame->realized_fontset_list = device->realized_fontset_list;
-
-  if (widget)
-    {
-      XtResource resources[] = {
-       { XtNfont, XtCFont, XtRString, sizeof (String),
-         XtOffset (AppDataPtr, font), XtRString, DEFAULT_FONT },
-       { XtNforeground, XtCForeground, XtRString, sizeof (String),
-         XtOffset (AppDataPtr, foreground), XtRString, "black" },
-       { XtNbackground, XtCBackground, XtRString, sizeof (String),
-         XtOffset (AppDataPtr, background), XtRString, "white" },
-       { XtNreverseVideo, XtCReverseVideo, XtRBoolean, sizeof (Boolean),
-         XtOffset (AppDataPtr, reverse_video), XtRImmediate, (caddr_t) FALSE }
-      };
-
-      XtGetApplicationResources (widget, &app_data,
-                                resources, XtNumber (resources), NULL, 0);
-      frame->foreground = msymbol (app_data.foreground);
-      frame->background = msymbol (app_data.background);
-      frame->videomode = app_data.reverse_video == True ? Mreverse : Mnormal;
-    }
-  else
-    {
-      app_data.font = DEFAULT_FONT;
-      frame->foreground = msymbol ("black");
-      frame->background = msymbol ("white");
-      frame->videomode = Mnormal;
-    }
-
-  {
-    int nfonts;
-    char **names = XListFonts (display, app_data.font, 1, &nfonts);
-
-    if (nfonts > 0)
-      {
-       if (! (frame->font = mfont_parse_name (names[0], Mx)))
-         {
-           /* The font name does not conform to XLFD.  Try to open the
-              font and get XA_FONT property.  */
-           XFontStruct *xfont = XLoadQueryFont (display, names[0]);
-
-           nfonts = 0;
-           if (xfont)
-             {
-               unsigned long value;
-               char *name;
-
-               if (XGetFontProperty (xfont, XA_FONT, &value)
-                   && (name = ((char *)
-                               XGetAtomName (display, (Atom) value))))
-                 {
-                   if ((frame->font = mfont_parse_name (name, Mx)))
-                     nfonts = 1;
-                 }
-               XFreeFont (display, xfont);
-             }
-         }
-       XFreeFontNames (names);
-      }
-    if (! nfonts)
-      frame->font = mfont_parse_name (FALLBACK_FONT, Mx);
-  }
-
-  face = mface_from_font (frame->font);
-  face->property[MFACE_FONTSET] = mfontset (NULL);
-  face->property[MFACE_FOREGROUND] = frame->foreground;
-  face->property[MFACE_BACKGROUND] = frame->background;
-  mface_put_prop (face, Mhline, mface_get_prop (mface__default, Mhline));
-  mface_put_prop (face, Mbox, mface_get_prop (mface__default, Mbox));
-  face->property[MFACE_VIDEOMODE] = frame->videomode;
-  mface_put_prop (face, Mhook_func, 
-                 mface_get_prop (mface__default, Mhook_func));
-  face->property[MFACE_RATIO] = (void *) 100;
-  mplist_push (param, Mface, face);
-  M17N_OBJECT_UNREF (face);
-
-#ifdef X_SET_ERROR_HANDLER
-  XSetErrorHandler (x_error_handler);
-  XSetIOErrorHandler (x_io_error_handler);
-#endif
-
-  return 0;
-}
-
-
 static void
 mwin__close_device (MFrame *frame)
 {
@@ -1822,139 +1556,408 @@ mwin__adjust_window (MFrame *frame, MDrawWindow win,
        new->width = 1;
       values.width = current->width = new->width;
     }
-  if (current->height != new->height)
+  if (current->height != new->height)
+    {
+      mask |= CWHeight;
+      if (new->height <= 0)
+       new->height = 1;
+      values.height = current->height = new->height;
+    }
+  if (current->x != new->x)
+    {
+      mask |= CWX;
+      values.x = current->x = new->x;
+    }
+  if (current->y != new->y)
+    {
+      mask |= CWY;
+      current->y = new->y;
+      values.y = current->y = new->y;
+    }
+  if (mask)
+    XConfigureWindow (display, (Window) win, mask, &values);
+  XClearWindow (display, (Window) win);
+}
+
+static MSymbol
+mwin__parse_event (MFrame *frame, void *arg, int *modifiers)
+{
+  XEvent *event = (XEvent *) arg;
+  MDisplayInfo *disp_info = FRAME_DEVICE (frame)->display_info;
+  int len;
+  char buf[512];
+  KeySym keysym;
+  MSymbol key;
+
+  *modifiers = 0;
+  if (event->xany.type != KeyPress
+      /* && event->xany.type != KeyRelease */
+      )
+    return Mnil;
+  len = XLookupString ((XKeyEvent *) event, (char *) buf, 512, &keysym, NULL);
+  if (len > 1)
+    return Mnil;
+  if (len == 1)
+    {
+      int c = keysym;
+
+      if (c < XK_space || c > XK_asciitilde)
+       c = buf[0];
+      if ((c == ' ' || c == 127) && ((XKeyEvent *) event)->state & ShiftMask)
+       *modifiers |= MINPUT_KEY_SHIFT_MODIFIER;
+      if (((XKeyEvent *) event)->state & ControlMask)
+       {
+         if (c >= 'a' && c <= 'z')
+           c += 'A' - 'a';
+         if (c >= ' ' && c < 127)
+           *modifiers |= MINPUT_KEY_CONTROL_MODIFIER;
+       }
+      key = minput__char_to_key (c);
+    }
+  else if (keysym >= XK_Shift_L && keysym <= XK_Hyper_R)
+    return Mnil;
+  else
+    {
+      char *str = XKeysymToString (keysym);
+
+      if (! str)
+       return Mnil;
+      key = msymbol (str);
+      if (((XKeyEvent *) event)->state & ShiftMask)
+       *modifiers |= MINPUT_KEY_SHIFT_MODIFIER;
+      if (((XKeyEvent *) event)->state & ControlMask)
+       *modifiers |= MINPUT_KEY_CONTROL_MODIFIER;
+    }
+  if (((XKeyEvent *) event)->state & disp_info->meta_mask)
+    *modifiers |= MINPUT_KEY_META_MODIFIER;
+  if (((XKeyEvent *) event)->state & disp_info->alt_mask)
+    *modifiers |= MINPUT_KEY_ALT_MODIFIER;
+  if (((XKeyEvent *) event)->state & disp_info->super_mask)
+    *modifiers |= MINPUT_KEY_SUPER_MODIFIER;
+  if (((XKeyEvent *) event)->state & disp_info->hyper_mask)
+    *modifiers |= MINPUT_KEY_HYPER_MODIFIER;
+
+  return key;
+}
+
+
+void
+mwin__dump_gc (MFrame *frame, MRealizedFace *rface)
+{
+  unsigned long valuemask = GCForeground | GCBackground | GCClipMask;
+  XGCValues values;
+  Display *display = FRAME_DISPLAY (frame);
+  GCInfo *info = rface->info;
+  int i;
+
+  for (i = 0; i <= GC_INVERSE; i++)
+    {
+      XGetGCValues (display, info->gc[i], valuemask, &values);
+      fprintf (stderr, "GC%d: fore/#%lX back/#%lX", i,
+              values.foreground, values.background);
+      fprintf (stderr, "\n");
+    }
+}
+
+static MDeviceDriver x_driver =
+  {
+    mwin__close_device,
+    mwin__device_get_prop,
+    mwin__realize_face,
+    mwin__free_realized_face,
+    mwin__fill_space,
+    mwin__draw_empty_boxes,
+    mwin__draw_hline,
+    mwin__draw_box,
+    mwin__draw_points,
+    mwin__region_from_rect,
+    mwin__union_rect_with_region,
+    mwin__intersect_region,
+    mwin__region_add_rect,
+    mwin__region_to_rect,
+    mwin__free_region,
+    mwin__dump_region,
+    mwin__create_window,
+    mwin__destroy_window,
+    mwin__map_window,
+    mwin__unmap_window,
+    mwin__window_geometry,
+    mwin__adjust_window,
+    mwin__parse_event
+  };
+
+/* Functions to be stored in MDeviceLibraryInterface by dlsym ().  */
+
+int
+device_init ()
+{
+  M_iso8859_1 = msymbol ("iso8859-1");
+  M_iso10646_1 = msymbol ("iso10646-1");
+
+  display_info_list = mplist ();
+  device_list = mplist ();
+
+#ifdef HAVE_XFT2
+  xft_driver.select = mfont__ft_driver.select;
+  xft_driver.encode_char = mfont__ft_driver.encode_char;
+#endif
+
+  Mxim = msymbol ("xim");
+  msymbol_put (Mxim, Minput_driver, &minput_xim_driver);
+
+  return 0;
+}
+
+int
+device_fini ()
+{
+  M17N_OBJECT_UNREF (display_info_list);
+  M17N_OBJECT_UNREF (device_list);
+  return 0;
+}
+
+/** Return an MWDevice object corresponding to a display specified in
+    PLIST.
+
+    It searches device_list for a device matching the display.  If
+    found, return the found object.  Otherwise, return a newly created
+    object.  */
+
+int
+device_open (MFrame *frame, MPlist *param)
+{
+  Display *display = NULL;
+  Screen *screen = NULL;
+  int screen_num;
+  Drawable drawable = 0;
+  Widget widget = NULL;
+  Colormap cmap = 0;
+  int auto_display = 0;
+  MDisplayInfo *disp_info = NULL;
+  MWDevice *device = NULL;
+  MSymbol key;
+  XWindowAttributes attr;
+  unsigned depth = 0;
+  MPlist *plist;
+  AppData app_data;
+  MFace *face;
+
+  for (plist = param; (key = mplist_key (plist)) != Mnil;
+       plist = mplist_next (plist))
+    {
+      if (key == Mdisplay)
+       display = (Display *) mplist_value (plist);
+      else if (key == Mscreen)
+       screen = mplist_value (plist);
+      else if (key == Mdrawable)
+       drawable = (Drawable) mplist_value (plist);
+      else if (key == Mdepth)
+       depth = (unsigned) mplist_value (plist);
+      else if (key == Mwidget)
+       widget = (Widget) mplist_value (plist);
+      else if (key == Mcolormap)
+       cmap = (Colormap) mplist_value (plist);
+    }
+
+  if (widget)
+    {
+      display = XtDisplay (widget);
+      screen_num = XScreenNumberOfScreen (XtScreen (widget));
+      depth = DefaultDepth (display, screen_num);
+    }
+  else if (drawable)
+    {
+      Window root_window;
+      int x, y;
+      unsigned width, height, border_width;
+
+      if (! display)
+       MERROR (MERROR_WIN, -1);
+      XGetGeometry (display, drawable, &root_window,
+                   &x, &y, &width, &height, &border_width, &depth);
+      XGetWindowAttributes (display, root_window, &attr);
+      screen_num = XScreenNumberOfScreen (attr.screen);
+    }
+  else
+    {
+      if (screen)
+       display = DisplayOfScreen (screen);
+      else
+       {
+         if (! display)
+           {
+             display = XOpenDisplay (NULL);
+             if (! display)
+               MERROR (MERROR_WIN, -1);
+             auto_display = 1;
+           }
+         screen = DefaultScreenOfDisplay (display);
+       }
+      screen_num = XScreenNumberOfScreen (screen);
+      if (! depth)
+       depth = DefaultDepth (display, screen_num);
+    }
+
+  if (! cmap)
+    cmap = DefaultColormap (display, screen_num);
+
+  for (plist = display_info_list; mplist_key (plist) != Mnil;
+       plist = mplist_next (plist))
+    {
+      disp_info = (MDisplayInfo *) mplist_value (plist);
+      if (disp_info->display == display)
+       break;
+    }
+
+  if (mplist_key (plist) != Mnil)
+    M17N_OBJECT_REF (disp_info);
+  else
     {
-      mask |= CWHeight;
-      if (new->height <= 0)
-       new->height = 1;
-      values.height = current->height = new->height;
-    }
-  if (current->x != new->x)
+      M17N_OBJECT (disp_info, free_display_info, MERROR_WIN);
+      disp_info->display = display;
+      disp_info->auto_display = auto_display;
+      disp_info->font_registry_list = mplist ();
+      disp_info->iso8859_1_family_list = mplist ();
+      disp_info->iso10646_1_family_list = mplist ();
+      disp_info->realized_font_list = mplist ();
+      find_modifier_bits (disp_info);
+      mplist_add (display_info_list, Mt, disp_info);
+    }  
+
+  for (plist = device_list; mplist_key (plist) != Mnil;
+       plist = mplist_next (plist))
     {
-      mask |= CWX;
-      values.x = current->x = new->x;
+      device = (MWDevice *) mplist_value (plist);
+      if (device->display_info == disp_info
+         && device->depth == depth
+         && device->cmap == cmap)
+       break;
     }
-  if (current->y != new->y)
+
+  if (mplist_key (plist) != Mnil)
+    M17N_OBJECT_REF (device);
+  else
     {
-      mask |= CWY;
-      current->y = new->y;
-      values.y = current->y = new->y;
+      unsigned long valuemask = GCForeground;
+      XGCValues values;
+
+      M17N_OBJECT (device, free_device, MERROR_WIN);
+      device->display_info = disp_info;
+      device->screen_num = screen_num;
+      /* A drawable on which to create GCs.  */
+      device->drawable = XCreatePixmap (display,
+                                       RootWindow (display, screen_num),
+                                       1, 1, depth);
+      device->depth = depth;
+      device->cmap = cmap;
+      device->realized_face_list = mplist ();
+      device->realized_fontset_list = mplist ();
+      device->gc_list = mplist ();
+      values.foreground = BlackPixel (display, screen_num);
+      device->scratch_gc = XCreateGC (display, device->drawable,
+                                     valuemask, &values);
+#ifdef HAVE_XFT2
+      device->xft_draw = XftDrawCreate (display, device->drawable,
+                                       DefaultVisual (display, screen_num),
+                                       cmap);
+#endif
     }
-  if (mask)
-    XConfigureWindow (display, (Window) win, mask, &values);
-  XClearWindow (display, (Window) win);
-}
 
-static MSymbol
-mwin__parse_event (MFrame *frame, void *arg, int *modifiers)
-{
-  XEvent *event = (XEvent *) arg;
-  MDisplayInfo *disp_info = FRAME_DEVICE (frame)->display_info;
-  int len;
-  char buf[512];
-  KeySym keysym;
-  MSymbol key;
+  frame->device = device;
+  frame->device_type = MDEVICE_SUPPORT_OUTPUT | MDEVICE_SUPPORT_INPUT;
+  frame->driver = &x_driver;
+  frame->font_driver_list = mplist ();
+  mplist_add (frame->font_driver_list, Mx, &xfont_driver);
+#ifdef HAVE_XFT2
+  mplist_add (frame->font_driver_list, Mfreetype, &xft_driver);
+#elif HAVE_FREETYPE
+  mplist_add (frame->font_driver_list, Mfreetype, &mfont__ft_driver);
+#endif
+  frame->realized_font_list = disp_info->realized_font_list;
+  frame->realized_face_list = device->realized_face_list;
+  frame->realized_fontset_list = device->realized_fontset_list;
 
-  *modifiers = 0;
-  if (event->xany.type != KeyPress
-      /* && event->xany.type != KeyRelease */
-      )
-    return Mnil;
-  len = XLookupString ((XKeyEvent *) event, (char *) buf, 512, &keysym, NULL);
-  if (len > 1)
-    return Mnil;
-  if (len == 1)
+  if (widget)
     {
-      int c = keysym;
+      XtResource resources[] = {
+       { XtNfont, XtCFont, XtRString, sizeof (String),
+         XtOffset (AppDataPtr, font), XtRString, DEFAULT_FONT },
+       { XtNforeground, XtCForeground, XtRString, sizeof (String),
+         XtOffset (AppDataPtr, foreground), XtRString, "black" },
+       { XtNbackground, XtCBackground, XtRString, sizeof (String),
+         XtOffset (AppDataPtr, background), XtRString, "white" },
+       { XtNreverseVideo, XtCReverseVideo, XtRBoolean, sizeof (Boolean),
+         XtOffset (AppDataPtr, reverse_video), XtRImmediate, (caddr_t) FALSE }
+      };
 
-      if (c < XK_space || c > XK_asciitilde)
-       c = buf[0];
-      if ((c == ' ' || c == 127) && ((XKeyEvent *) event)->state & ShiftMask)
-       *modifiers |= MINPUT_KEY_SHIFT_MODIFIER;
-      if (((XKeyEvent *) event)->state & ControlMask)
-       {
-         if (c >= 'a' && c <= 'z')
-           c += 'A' - 'a';
-         if (c >= ' ' && c < 127)
-           *modifiers |= MINPUT_KEY_CONTROL_MODIFIER;
-       }
-      key = minput__char_to_key (c);
+      XtGetApplicationResources (widget, &app_data,
+                                resources, XtNumber (resources), NULL, 0);
+      frame->foreground = msymbol (app_data.foreground);
+      frame->background = msymbol (app_data.background);
+      frame->videomode = app_data.reverse_video == True ? Mreverse : Mnormal;
     }
-  else if (keysym >= XK_Shift_L && keysym <= XK_Hyper_R)
-    return Mnil;
   else
     {
-      char *str = XKeysymToString (keysym);
-
-      if (! str)
-       return Mnil;
-      key = msymbol (str);
-      if (((XKeyEvent *) event)->state & ShiftMask)
-       *modifiers |= MINPUT_KEY_SHIFT_MODIFIER;
-      if (((XKeyEvent *) event)->state & ControlMask)
-       *modifiers |= MINPUT_KEY_CONTROL_MODIFIER;
+      app_data.font = DEFAULT_FONT;
+      frame->foreground = msymbol ("black");
+      frame->background = msymbol ("white");
+      frame->videomode = Mnormal;
     }
-  if (((XKeyEvent *) event)->state & disp_info->meta_mask)
-    *modifiers |= MINPUT_KEY_META_MODIFIER;
-  if (((XKeyEvent *) event)->state & disp_info->alt_mask)
-    *modifiers |= MINPUT_KEY_ALT_MODIFIER;
-  if (((XKeyEvent *) event)->state & disp_info->super_mask)
-    *modifiers |= MINPUT_KEY_SUPER_MODIFIER;
-  if (((XKeyEvent *) event)->state & disp_info->hyper_mask)
-    *modifiers |= MINPUT_KEY_HYPER_MODIFIER;
 
-  return key;
-}
+  {
+    int nfonts;
+    char **names = XListFonts (display, app_data.font, 1, &nfonts);
 
+    if (nfonts > 0)
+      {
+       if (! (frame->font = mfont_parse_name (names[0], Mx)))
+         {
+           /* The font name does not conform to XLFD.  Try to open the
+              font and get XA_FONT property.  */
+           XFontStruct *xfont = XLoadQueryFont (display, names[0]);
 
-void
-mwin__dump_gc (MFrame *frame, MRealizedFace *rface)
-{
-  unsigned long valuemask = GCForeground | GCBackground | GCClipMask;
-  XGCValues values;
-  Display *display = FRAME_DISPLAY (frame);
-  GCInfo *info = rface->info;
-  int i;
+           nfonts = 0;
+           if (xfont)
+             {
+               unsigned long value;
+               char *name;
 
-  for (i = 0; i <= GC_INVERSE; i++)
-    {
-      XGetGCValues (display, info->gc[i], valuemask, &values);
-      fprintf (stderr, "GC%d: fore/#%lX back/#%lX", i,
-              values.foreground, values.background);
-      fprintf (stderr, "\n");
-    }
-}
+               if (XGetFontProperty (xfont, XA_FONT, &value)
+                   && (name = ((char *)
+                               XGetAtomName (display, (Atom) value))))
+                 {
+                   if ((frame->font = mfont_parse_name (name, Mx)))
+                     nfonts = 1;
+                 }
+               XFreeFont (display, xfont);
+             }
+         }
+       XFreeFontNames (names);
+      }
+    if (! nfonts)
+      frame->font = mfont_parse_name (FALLBACK_FONT, Mx);
+  }
 
-static MDeviceDriver x_driver =
-  {
-    0,
-    mwin__device_init,
-    mwin__device_fini,
-    mwin__open_device,
-    mwin__close_device,
-    mwin__device_get_prop,
-    mwin__realize_face,
-    mwin__free_realized_face,
-    mwin__fill_space,
-    mwin__draw_empty_boxes,
-    mwin__draw_hline,
-    mwin__draw_box,
-    mwin__draw_points,
-    mwin__region_from_rect,
-    mwin__union_rect_with_region,
-    mwin__intersect_region,
-    mwin__region_add_rect,
-    mwin__region_to_rect,
-    mwin__free_region,
-    mwin__dump_region,
-    mwin__create_window,
-    mwin__destroy_window,
-    mwin__map_window,
-    mwin__unmap_window,
-    mwin__window_geometry,
-    mwin__adjust_window,
-    mwin__parse_event
-  };
+  face = mface_from_font (frame->font);
+  face->property[MFACE_FONTSET] = mfontset (NULL);
+  face->property[MFACE_FOREGROUND] = frame->foreground;
+  face->property[MFACE_BACKGROUND] = frame->background;
+  mface_put_prop (face, Mhline, mface_get_prop (mface__default, Mhline));
+  mface_put_prop (face, Mbox, mface_get_prop (mface__default, Mbox));
+  face->property[MFACE_VIDEOMODE] = frame->videomode;
+  mface_put_prop (face, Mhook_func, 
+                 mface_get_prop (mface__default, Mhook_func));
+  face->property[MFACE_RATIO] = (void *) 100;
+  mplist_push (param, Mface, face);
+  M17N_OBJECT_UNREF (face);
+
+#ifdef X_SET_ERROR_HANDLER
+  XSetErrorHandler (x_error_handler);
+  XSetIOErrorHandler (x_io_error_handler);
+#endif
+
+  return 0;
+}
 
 \f
 
@@ -2164,26 +2167,13 @@ x_io_error_handler (Display *display)
 }
 #endif
 
+/*=*/
+
 /*** @} */
 #endif /* !FOR_DOXYGEN || DOXYGEN_INTERNAL_MODULE */
 \f
 /* External API */
 
-int
-m17n_init_X ()
-{
-  x_driver.initialized = 0;
-  mplist_put (m17n__device_library_list, Mx, &x_driver);
-
-#ifdef HAVE_XFT2
-  xft_driver.select = mfont__ft_driver.select;
-  xft_driver.encode_char = mfont__ft_driver.encode_char;
-#endif
-
-  return 0;
-}
-
-/*=*/
 /*** @addtogroup m17nInputMethodWin */
 /*=*/
 /*** @{ */
index 4bc4c3e..3dc953b 100644 (file)
 #include <X11/Xutil.h>
 #include <X11/Xresource.h>
 
-#ifndef _M17N_GUI_H_
-#include <m17n-gui.h>
-#endif
-
 #ifdef __cplusplus
 extern "C"
 {
 #endif
 
-extern int m17n_init_X (void);
-#undef M17N_INIT_X
-#define M17N_INIT_X() m17n_init_X ()
-
-#undef M17N_INIT
-#define M17N_INIT()                    \
-  do {                                 \
-    if (m17n_init_win () < 0) break;   \
-    if (M17N_INIT_GD () < 0) break;    \
-    M17N_INIT_X ();                    \
-  } while (0)
-
 /* For inputting.  */
 
 extern MInputDriver minput_xim_driver;
index 9a8bf40..3e1ce7a 100644 (file)
@@ -319,71 +319,6 @@ gd_render (MDrawWindow win, int x, int y,
 static MFontDriver gd_font_driver =
   { NULL, NULL, NULL, NULL, gd_render };
 
-static int
-gd_init ()
-{
-  M_rgb = msymbol ("  rgb");
-  read_rgb_txt ();
-  realized_fontset_list = mplist ();
-  realized_font_list = mplist ();
-  realized_face_list = mplist ();  
-  scratch_images[0] = scratch_images[1] = NULL;
-
-  gd_font_driver.select = mfont__ft_driver.select;
-  gd_font_driver.open = mfont__ft_driver.open;
-  gd_font_driver.find_metric = mfont__ft_driver.find_metric;
-  gd_font_driver.encode_char = mfont__ft_driver.encode_char;
-
-  return 0;
-}
-
-static int
-gd_fini ()
-{
-  MPlist *plist;
-  int i;
-
-  MPLIST_DO (plist, realized_fontset_list)
-    mfont__free_realized_fontset ((MRealizedFontset *) MPLIST_VAL (plist));
-  M17N_OBJECT_UNREF (realized_fontset_list);
-
-  MPLIST_DO (plist, realized_face_list)
-    {
-      MRealizedFace *rface = MPLIST_VAL (plist);
-
-      free (rface->info);
-      mface__free_realized (rface);
-    }
-  M17N_OBJECT_UNREF (realized_face_list);
-
-  MPLIST_DO (plist, realized_font_list)
-    mfont__free_realized ((MRealizedFont *) MPLIST_VAL (plist));
-  M17N_OBJECT_UNREF (realized_font_list);
-
-  for (i = 0; i < 2; i++)
-    if (scratch_images[i])
-      gdImageDestroy (scratch_images[i]);
-  return 0;
-}
-
-static int
-gd_open (MFrame *frame, MPlist *param)
-{
-  MFace *face;
-
-  frame->device = NULL;
-  frame->device_type = MDEVICE_SUPPORT_OUTPUT;
-  frame->font_driver_list = mplist ();
-  mplist_add (frame->font_driver_list, Mfreetype, &gd_font_driver);
-  frame->realized_font_list = realized_font_list;
-  frame->realized_face_list = realized_face_list;
-  frame->realized_fontset_list = realized_fontset_list;
-  face = mface_copy (mface__default);
-  mplist_push (param, Mface, face);
-  M17N_OBJECT_UNREF (face);
-  return 0;
-}
-
 static void
 gd_close (MFrame *frame)
 {
@@ -774,10 +709,6 @@ gd_dump_region (MDrawRegion region)
 
 static MDeviceDriver gd_driver =
   {
-    0,
-    gd_init,
-    gd_fini,
-    gd_open,
     gd_close,
     gd_get_prop,
     gd_realize_face,
@@ -796,22 +727,72 @@ static MDeviceDriver gd_driver =
     gd_dump_region,
   };
 
-\f
-/* External API */
+/* Functions to be stored in MDeviceLibraryInterface by dlsym ().  */
+
 int
-m17n_init_gd ()
+device_init ()
 {
-  gd_driver.initialized = 0;
-  mplist_put (m17n__device_library_list, Mgd, &gd_driver);
+  M_rgb = msymbol ("  rgb");
+  read_rgb_txt ();
+  realized_fontset_list = mplist ();
+  realized_font_list = mplist ();
+  realized_face_list = mplist ();  
+  scratch_images[0] = scratch_images[1] = NULL;
+
+  gd_font_driver.select = mfont__ft_driver.select;
+  gd_font_driver.open = mfont__ft_driver.open;
+  gd_font_driver.find_metric = mfont__ft_driver.find_metric;
+  gd_font_driver.encode_char = mfont__ft_driver.encode_char;
+
   return 0;
 }
 
-#else  /* not HAVE_GD nor HAVE_FREETYPE */
+int
+device_fini ()
+{
+  MPlist *plist;
+  int i;
+
+  MPLIST_DO (plist, realized_fontset_list)
+    mfont__free_realized_fontset ((MRealizedFontset *) MPLIST_VAL (plist));
+  M17N_OBJECT_UNREF (realized_fontset_list);
+
+  MPLIST_DO (plist, realized_face_list)
+    {
+      MRealizedFace *rface = MPLIST_VAL (plist);
+
+      free (rface->info);
+      mface__free_realized (rface);
+    }
+  M17N_OBJECT_UNREF (realized_face_list);
+
+  MPLIST_DO (plist, realized_font_list)
+    mfont__free_realized ((MRealizedFont *) MPLIST_VAL (plist));
+  M17N_OBJECT_UNREF (realized_font_list);
+
+  for (i = 0; i < 2; i++)
+    if (scratch_images[i])
+      gdImageDestroy (scratch_images[i]);
+  return 0;
+}
 
 int
-m17n_init_gd ()
+device_open (MFrame *frame, MPlist *param)
 {
-  return -1;
+  MFace *face;
+
+  frame->device = NULL;
+  frame->device_type = MDEVICE_SUPPORT_OUTPUT;
+  frame->driver = &gd_driver;
+  frame->font_driver_list = mplist ();
+  mplist_add (frame->font_driver_list, Mfreetype, &gd_font_driver);
+  frame->realized_font_list = realized_font_list;
+  frame->realized_face_list = realized_face_list;
+  frame->realized_fontset_list = realized_fontset_list;
+  face = mface_copy (mface__default);
+  mplist_push (param, Mface, face);
+  M17N_OBJECT_UNREF (face);
+  return 0;
 }
 
 #endif /* not HAVE_GD nor HAVE_FREETYPE */
index b752f1b..728280a 100644 (file)
@@ -85,6 +85,27 @@ static int win_initialized;
 #define DLOPEN_SHLIB_EXT ".so"
 #endif
 
+/** Information about a dynamic library supporting a specific graphic
+    device.  */
+typedef struct
+{
+  /** Name of the dynamic library (e.g. "libm17n-X.so").  */
+  char *library;
+  /** Handle fo the dynamic library.  */
+  void *handle;
+  /** Function to call just after loading the library.  */
+  int (*init) ();
+  /** Function to call to open a frame on the graphic device.  */
+  int (*open) (MFrame *frame, MPlist *param);
+  /** Function to call just before unloading the library.  */
+  int (*fini) ();
+} MDeviceLibraryInterface;
+
+
+/** Plist of device symbol vs MDeviceLibraryInterface.  */
+
+static MPlist *device_library_list;
+
 /** Close MFrame and free it.  */
 
 static void
@@ -99,6 +120,24 @@ free_frame (void *object)
   free (object);
 }
 
+
+/** Register a dynamic library of name LIB by a key NAME.  */
+
+static int
+register_device_library (MSymbol name, char *lib)
+{
+  MDeviceLibraryInterface *interface;
+
+  MSTRUCT_CALLOC (interface, MERROR_WIN);
+  interface->library = malloc (strlen (lib) 
+                              + strlen (DLOPEN_SHLIB_EXT) + 1);
+  sprintf (interface->library, "%s%s", lib, DLOPEN_SHLIB_EXT);
+  if (! device_library_list)
+    device_library_list = mplist ();
+  mplist_add (device_library_list, name, interface);
+  return 0;
+}
+
 \f
 #ifdef HAVE_FREETYPE
 /** Null device support.  */
@@ -109,6 +148,36 @@ static struct {
   MPlist *realized_face_list;
 } null_device;
 
+static void
+null_device_close (MFrame *frame)
+{
+}
+
+static void *
+null_device_get_prop (MFrame *frame, MSymbol key)
+{
+  return NULL;
+}
+
+static void
+null_device_realize_face (MRealizedFace *rface)
+{
+  rface->info = NULL;
+}
+
+static void
+null_device_free_realized_face (MRealizedFace *rface)
+{
+}
+
+static MDeviceDriver null_driver =
+  {
+    null_device_close,
+    null_device_get_prop,
+    null_device_realize_face,
+    null_device_free_realized_face
+  };
+
 static int
 null_device_init ()
 {
@@ -144,6 +213,7 @@ null_device_open (MFrame *frame, MPlist *param)
 
   frame->device = NULL;
   frame->device_type = 0;
+  frame->driver = &null_driver;
   frame->font_driver_list = mplist ();
   mplist_add (frame->font_driver_list, Mfreetype, &mfont__ft_driver);
   frame->realized_font_list = null_device.realized_font_list;
@@ -155,39 +225,8 @@ null_device_open (MFrame *frame, MPlist *param)
   return 0;
 }
 
-static void
-null_device_close (MFrame *frame)
-{
-}
-
-static void *
-null_device_get_prop (MFrame *frame, MSymbol key)
-{
-  return NULL;
-}
-
-static void
-null_device_realize_face (MRealizedFace *rface)
-{
-  rface->info = NULL;
-}
-
-static void
-null_device_free_realized_face (MRealizedFace *rface)
-{
-}
-
-static MDeviceDriver null_driver =
-  {
-    0,
-    null_device_init,
-    null_device_fini,
-    null_device_open,
-    null_device_close,
-    null_device_get_prop,
-    null_device_realize_face,
-    null_device_free_realized_face
-  };
+static MDeviceLibraryInterface null_interface =
+  { NULL, NULL, null_device_init, null_device_open, null_device_fini };
 
 #endif
 \f
@@ -195,11 +234,6 @@ static MDeviceDriver null_driver =
 
 MSymbol Mfreetype;
 
-/** Plist of device symbol vs functions to initialized the device
-    library.  */
-MPlist *m17n__device_library_list;
-
-
 /*** @} */ 
 #endif /* !FOR_DOXYGEN || DOXYGEN_INTERNAL_MODULE */
 
@@ -235,6 +269,9 @@ m17n_init_win (void)
   Mdepth = msymbol ("depth");
   Mwidget = msymbol ("widget");
 
+  register_device_library (Mx, "libm17n-X");
+  register_device_library (Mgd, "libm17n-gd");
+
   MDEBUG_PUSH_TIME ();
   if (mfont__init () < 0)
     goto err;
@@ -252,13 +289,6 @@ m17n_init_win (void)
     goto err;
   MDEBUG_PRINT_TIME ("INIT", (stderr, " to initialize input-win module."));
   mframe_default = NULL;
-
-  m17n__device_library_list = mplist ();
-#ifdef HAVE_FREETYPE
-  null_driver.initialized = 0;
-  mplist_put (m17n__device_library_list, Mt, &null_driver);
-#endif
-
   return 0;
 
  err:
@@ -283,17 +313,22 @@ m17n_fini_win (void)
       MDEBUG_PUSH_TIME ();
       MDEBUG_PUSH_TIME ();
       MDEBUG_PRINT_TIME ("FINI", (stderr, " to finalize device modules."));
-      MPLIST_DO (plist, m17n__device_library_list)
+      MPLIST_DO (plist, device_library_list)
        {
-         MDeviceDriver *driver = MPLIST_VAL (plist);
+         MDeviceLibraryInterface *interface = MPLIST_VAL (plist);
 
-         if (driver->initialized)
+         if (interface->handle && interface->fini)
            {
-             (*driver->fini) ();
-             driver->initialized = 0;
+             (*interface->fini) ();
+             dlclose (interface->handle);
            }
+         free (interface->library);
        }
-      M17N_OBJECT_UNREF (m17n__device_library_list);
+#ifdef HAVE_FREETYPE
+      if (null_interface.handle)
+       (*null_interface.fini) ();
+#endif /* not HAVE_FREETYPE */
+      M17N_OBJECT_UNREF (device_library_list);
       MDEBUG_PRINT_TIME ("FINI", (stderr, " to finalize input-gui module."));
       minput__win_fini ();
       MDEBUG_PRINT_TIME ("FINI", (stderr, " to finalize draw module."));
@@ -564,19 +599,13 @@ mframe (MPlist *plist)
   int plist_created = 0;
   MPlist *pl;
   MSymbol device;
-  MDeviceDriver *driver;
+  MDeviceLibraryInterface *interface;
 
   if (plist)
     {
       pl = mplist_find_by_key (plist, Mdevice);
       if (pl)
-       {
-         device = MPLIST_VAL (pl);
-         if (device == Mt)
-           MERROR (MERROR_WIN, NULL);
-         if (device == Mnil)
-           device = Mt;
-       }
+       device = MPLIST_VAL (pl);
       else
        device = Mx;
     }
@@ -587,23 +616,47 @@ mframe (MPlist *plist)
       device = Mx;
     }
 
-  driver = mplist_get (m17n__device_library_list, device);
-  if (! driver)
-    MERROR (MERROR_WIN, NULL);
-  if (! driver->initialized)
+  if (device == Mnil)
     {
-      if ((*driver->init) () < 0)
+#ifdef HAVE_FREETYPE
+      interface = &null_interface;
+      if (! interface->handle)
+       {
+         (*interface->init) ();
+         interface->handle = (void *) 1;
+       }
+#else  /* not HAVE_FREETYPE */
+      MERROR (MERROR_WIN, NULL);
+#endif /* not HAVE_FREETYPE */
+    }
+  else
+    {
+      interface = mplist_get (device_library_list, device);
+      if (! interface)
        MERROR (MERROR_WIN, NULL);
-      driver->initialized = 1;
-    }      
+      if (! interface->handle)
+       {
+         interface->handle = dlopen (interface->library, RTLD_NOW);
+         if (! interface->handle)
+           MERROR (MERROR_WIN, NULL);
+         interface->init = dlsym (interface->handle, "device_init");
+         interface->open = dlsym (interface->handle, "device_open");
+         interface->fini = dlsym (interface->handle, "device_fini");
+         if (! interface->init || ! interface->open || ! interface->fini
+             || (*interface->init) () < 0)
+           {
+             dlclose (interface->handle);
+             MERROR (MERROR_WIN, NULL);
+           }
+       }
+    }
 
   M17N_OBJECT (frame, free_frame, MERROR_FRAME);
-  if ((*driver->open) (frame, plist) < 0)
+  if ((*interface->open) (frame, plist) < 0)
     {
       free (frame);
       MERROR (MERROR_WIN, NULL);
     }
-  frame->driver = driver;
 
   if (! mframe_default)
     mframe_default = frame;
index ce2f597..48f545b 100644 (file)
@@ -32,9 +32,6 @@ extern "C"
 {
 #endif
 
-#define M17N_INIT_X() 1
-#define M17N_INIT_GD() 1
-
 extern int m17n_init_win (void);
 #undef M17N_INIT
 #define M17N_INIT() m17n_init_win ()