*** empty log message ***
[m17n/m17n-test.git] / flt.c
diff --git a/flt.c b/flt.c
index dbf6c88..5b5c9c4 100644 (file)
--- a/flt.c
+++ b/flt.c
@@ -113,11 +113,23 @@ new_face (char *fontname, char **err)
 
 #ifdef FLT_GUI
 
-typedef struct
+typedef struct _MFLTFont MFLTFont;
+
+struct _MFLTFont
 {
+  int x_ppem, y_ppem;
+  void (*get_glyph_id) (void);
+  void (*get_metric) (void);
+  void (*suitable_p) (void);
+  void (*drive_otf) (void);
   MFont *font;
   FT_Face face;
-} MFLTFont;
+};
+
+void get_glyph_id (void) {}
+void get_metric (void) {}
+void suitable_p (void) {}
+void drive_otf (void) {}
 
 MFrame *frame;
 
@@ -157,21 +169,6 @@ close_font (MFLTFont *font)
   m17n_object_unref (frame);
 }
 
-int
-flt (MText *mt, int from, int to, MFLTFont *font, char *flt_name)
-{
-  MDrawControl control;
-
-  memset (&control, 0, sizeof (MDrawControl));
-  control.two_dimensional = 1;
-  control.enable_bidi = 1;
-  control.anti_alias = 1;
-  /*control.disable_caching = 1;*/
-  mtext_put_prop (mt, from, to, Mfont, font->font);
-  mdraw_text_extents (frame, mt, from, to, &control, NULL, NULL, NULL);
-  return 0;
-}
-
 #elif defined (FLT_OTF) || defined (FLT_HB)
 
 typedef struct {
@@ -212,23 +209,6 @@ get_metric (MFLTFont *font, MFLTGlyphString *gstring, int from, int to)
   return 0;
 }
 
-int
-flt (MText *mt, int from, int to, MFLTFont *font, char *flt_name)
-{
-  MFLTGlyphString gstring;
-  int len = to - from;
-  int i;
-
-  memset (&gstring, 0, sizeof (MFLTGlyphString));
-  gstring.glyph_size = sizeof (MFLTGlyph);
-  gstring.allocated = len * 2;
-  gstring.glyphs = alloca (sizeof (MFLTGlyph) * gstring.allocated);
-  for (i = 0; i < len; i++)
-    gstring.glyphs[i].c = mtext_ref_char (mt, from + i);
-  gstring.used = len;
-  return mflt_run (&gstring, 0, len, font, msymbol (flt_name));
-}
-
 #ifdef FLT_OTF
 
 typedef struct {
@@ -741,7 +721,6 @@ setup_features (int gsubp, FontInfoHB *font_info, MFLTOtfSpec *spec,
   FT_UShort req_feature, index;
   FT_UInt *feature_list;
   int i, j, k;
-  HB_Error err;
 
   if (gsubp)
     {
@@ -1022,10 +1001,13 @@ get_glyph_id (MFLTFont *font, MFLTGlyph *g)
 {
   FontInfoPango *font_info = (FontInfoPango *) font;
 
-  g->code = pango_fc_font_get_glyph (font_info->pango_font, g->c);
+  g->code = pango_fc_font_get_glyph (font_info->pango_font, g->code);
   return (g->code ? 0 : -1);
 }
 
+#define PANGO_SCALE_TO_26_6 (PANGO_SCALE / (1<<6))
+
+#if 0
 int
 get_metric (MFLTFont *font, MFLTGlyphString *gstring, int from, int to)
 {
@@ -1039,14 +1021,18 @@ get_metric (MFLTFont *font, MFLTGlyphString *gstring, int from, int to)
 
       pango_font_get_glyph_extents (PANGO_FONT (font_info->pango_font),
                                    gstring->glyphs[i].code, &inc, &logical);
-      g->lbearing = inc.x;
-      g->rbearing = inc.x + inc.width;
-      g->xadv = logical.width;
+      g->lbearing = inc.x / PANGO_SCALE_TO_26_6;
+      g->rbearing = (inc.x + inc.width) / PANGO_SCALE_TO_26_6;
+      g->xadv = logical.width / PANGO_SCALE_TO_26_6;
       g->yadv = 0;
-      g->ascent = - inc.y;
-      g->descent = inc.height + inc.y;
+      g->ascent = - inc.y / PANGO_SCALE_TO_26_6;
+      g->descent = (inc.height + inc.y) / PANGO_SCALE_TO_26_6;
     }
+  return 0;
 }
+#else
+int (*get_metric) (MFLTFont *font, MFLTGlyphString *gstring, int from, int to) = NULL;
+#endif
 
 #ifndef PANGO_OT_DEFAULT_LANGUAGE
 #define PANGO_OT_DEFAULT_LANGUAGE ((guint) 0xFFFF)
@@ -1065,7 +1051,6 @@ setup_features (PangoOTTableType type, FontInfoPango *font_info,
   guint req_feature, index;
   guint *feature_list;
   int i, j, k;
-  int err;
   FT_Face face;
   PangoOTInfo *ot_info; 
 
@@ -1132,9 +1117,15 @@ setup_features (PangoOTTableType type, FontInfoPango *font_info,
       }
   info->count = i;
   info->ruleset = pango_ot_ruleset_new (ot_info);
+#if 1
   for (i = 0; i < info->count; i++)
     pango_ot_ruleset_add_feature (info->ruleset, type, info->indices[i],
                                  PANGO_OT_ALL_GLYPHS);
+#else
+  for (i = info->count - 1; i >= 0; i--)
+    pango_ot_ruleset_add_feature (info->ruleset, type, info->indices[i],
+                                 PANGO_OT_ALL_GLYPHS);
+#endif
 }
 
 GsubGposInfo *
@@ -1186,9 +1177,9 @@ drive_otf (MFLTFont *font, MFLTOtfSpec *spec,
       g = out->glyphs + out->used++;
       if (g->code != glyph_info->glyph)
        g->c = 0, g->code = glyph_info->glyph;
-      g->xoff = glyph_info->geometry.x_offset;
-      g->yoff = glyph_info->geometry.y_offset;
-      g->xadv = glyph_info->geometry.width;
+      g->xoff = glyph_info->geometry.x_offset / PANGO_SCALE_TO_26_6;
+      g->yoff = glyph_info->geometry.y_offset / PANGO_SCALE_TO_26_6;
+      g->xadv = glyph_info->geometry.width / PANGO_SCALE_TO_26_6;
       g->yadv = 0;
       adjustment[i].set = 0;
     }
@@ -1254,25 +1245,77 @@ close_font (MFLTFont *font)
   g_object_unref (font_info->fontmap);
 }
 
+#endif
+
+#ifdef FLT_GUI
+
 int
-flt (MText *mt, int from, int to, MFLTFont *font, char *flt_name)
+run_flt (MText *mt, int from, int to, MFLTFont *font, char *flt_name)
 {
-  MFLTGlyphString gstring;
-  int len = to - from;
-  int i;
+  MDrawControl control;
 
-  memset (&gstring, 0, sizeof (MFLTGlyphString));
-  gstring.glyph_size = sizeof (MFLTGlyph);
-  gstring.allocated = len * 2;
-  gstring.glyphs = alloca (sizeof (MFLTGlyph) * gstring.allocated);
-  for (i = 0; i < len; i++)
-    gstring.glyphs[i].c = mtext_ref_char (mt, from + i);
-  gstring.used = len;
-  return mflt_run (&gstring, 0, len, font, msymbol (flt_name));
+  memset (&control, 0, sizeof (MDrawControl));
+  control.two_dimensional = 1;
+  control.enable_bidi = 1;
+  control.anti_alias = 1;
+  /*control.disable_caching = 1;*/
+  mtext_put_prop (mt, from, to, Mfont, font->font);
+  mdraw_text_extents (frame, mt, from, to, &control, NULL, NULL, NULL);
+  return 0;
 }
 
+#else
+
+int
+run_flt (MText *mt, int from, int to, MFLTFont *font, char *flt_name)
+{
+  static MFLT *flt = NULL;
+  MCharTable *coverage;
+  static MFLTGlyphString gstring;
+
+  if (! flt
+      && ! (flt = mflt_get (flt_name)))
+    {
+      fprintf (stderr, "Invalid FLT name: %s\n", flt_name);
+      exit (1);
+    }
+  coverage = mflt_coverage (flt);
+  while (from < to)
+    {
+      int len = 0, i;
+
+      for (; from < to; from++)
+       if (mchartable_lookup (coverage, mtext_ref_char (mt, from)))
+         {
+           for (i = from + 1; i < to; i++)
+             if (! mchartable_lookup (coverage, mtext_ref_char (mt, i)))
+               break;
+           len = i - from;
+           break;
+         }
+      if (len > 0)
+       {
+         if (gstring.allocated < len)
+           {
+             gstring.allocated = len * 2;
+             gstring.glyphs = realloc (gstring.glyphs,
+                                       sizeof (MFLTGlyph) * len * 2);
+           }
+         gstring.glyph_size = sizeof (MFLTGlyph);
+         for (i = 0; i < len; i++)
+           gstring.glyphs[i].c = mtext_ref_char (mt, from + i);
+         gstring.used = len;
+         i = mflt_run (&gstring, 0, len, font, flt);
+         if (i < 0)
+           return i;
+         from += len;
+       }
+    }
+  return to;
+}
 #endif
 
+
 int
 main (int argc, char **argv)
 {
@@ -1308,13 +1351,17 @@ main (int argc, char **argv)
   for (i = 0, j = mtext_character (mt, i, len, '\n'); i < len;
        i = j + 1, j = mtext_character (mt, i, len, '\n'))
     {
+      int to;
+
       if (j < 0)
        j = len;
-      if (flt (mt, i, j, font, flt_name) < 0)
+      to = run_flt (mt, i, j, font, flt_name);
+      if (to < 0)
        {
          fprintf (stderr, "Error in FLT processing.\n");
          exit (1);
        }
+      i = j;
     }
   m17n_object_unref (mt);
   close_font (font);