[poppler] poppler/poppler: CairoFontEngine.cc, 1.5, 1.6 CairoFontEngine.h, 1.2, 1.3 CairoOutputDev.cc, 1.6, 1.7

Kristian Hogsberg krh at freedesktop.org
Thu Apr 21 21:09:25 PDT 2005


Update of /cvs/poppler/poppler/poppler
In directory gabe:/tmp/cvs-serv3183/poppler

Modified Files:
	CairoFontEngine.cc CairoFontEngine.h CairoOutputDev.cc 
Log Message:
Fri Apr 22 00:01:40 2005  Kristian Høgsberg  <krh at redhat.com>

        * poppler/CairoFontEngine.cc: Hack around semi-broken cairo-0.4.0
        font API to fix the problem where some glyphs would show up at the
        wrong sizes.  We now create an FT_Face for each size and font
        combination we encounter, since an FT_Face can't be shared between
        several cairo_font_t.



Index: CairoFontEngine.cc
===================================================================
RCS file: /cvs/poppler/poppler/poppler/CairoFontEngine.cc,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -d -r1.5 -r1.6
--- CairoFontEngine.cc	21 Apr 2005 06:35:33 -0000	1.5
+++ CairoFontEngine.cc	22 Apr 2005 04:09:23 -0000	1.6
@@ -60,7 +60,15 @@
 // CairoFont
 //------------------------------------------------------------------------
 
-CairoFont::CairoFont(GfxFont *gfxFont, XRef *xref, FT_Library lib) {
+/* For the 0.3 release of poppler we're creating a CairoFont, and
+ * thus, an FT_Face for each size of each font we encounter.  We
+ * should of course be able to share FT_Face instances across all
+ * sizes of a font.  However, to do that we need to be able to create
+ * a cairo_unscaled_font_t, which is not possible with the cairo-0.4.0
+ * API which is what we're targeting with this release. */
+
+CairoFont::CairoFont(GfxFont *gfxFont, XRef *xref, FT_Library lib, 
+		     double m11, double m12, double m21, double m22) {
   Ref embRef;
   Object refObj, strObj;
   GooString *tmpFileName, *fileName, *substName,*tmpFileName2;
@@ -77,7 +85,6 @@
   codeToGIDLen = 0;
   substIdx = -1;
   cairo_font = NULL;
-  instance_list = NULL;
   
   ref = *gfxFont->getID();
   fontType = gfxFont->getType();
@@ -232,6 +239,19 @@
     unlink (fileName->getCString());
   }
 
+  this->m11 = m11;
+  this->m12 = m12;
+  this->m21 = m21;
+  this->m22 = m22;
+  cairo_matrix_t *matrix = cairo_matrix_create ();
+  cairo_matrix_set_affine (matrix, m11, m12, m21, m22, 0, 0);
+  cairo_font = cairo_ft_font_create_for_ft_face (face, FT_LOAD_NO_HINTING,
+						 matrix);
+  cairo_matrix_destroy (matrix);
+  if (cairo_font == NULL)
+    goto err2; /* this doesn't do anything, but it looks like we're
+		* handling the error */
+
   return;
  err2:
   /* hmm? */
@@ -239,13 +259,7 @@
 }
 
 CairoFont::~CairoFont() {
-  Instance *i, *next;
-
-  for (i = instance_list; i != NULL; i = next) {
-    next = i->next;
-    cairo_font_destroy (i->font);
-    delete i;
-  }
+  cairo_font_destroy (cairo_font);
 
   /* cairo_font_t's created from an FT_Face are never cached so we can
    * free the font here.  There might be glyphs in the cairo glyph
@@ -256,36 +270,16 @@
 }
 
 GBool
-CairoFont::matches(Ref &other) {
-  return (other.num == ref.num &&
-	  other.gen == ref.gen);
+CairoFont::matches(Ref &other,
+		   double m11, double m12, double m21, double m22) {
+  return (other.num == ref.num && other.gen == ref.gen &&
+	  this->m11 == m11 && this->m12 == m12 &&
+	  this->m21 == m21 && this->m22 == m22);
 }
 
 cairo_font_t *
-CairoFont::getFont(double a, double b, double c, double d) {
-  Instance *i;
-  cairo_matrix_t *matrix;
-
-  for (i = instance_list; i != NULL; i = i->next) {
-    if (i->a == a && i->b == b && i->c == c && i->d == d)
-      return i->font;
-  }
-
-  i = new Instance;
-  i->a = a;
-  i->b = b;
-  i->c = c;
-  i->d = d;
-
-  matrix = cairo_matrix_create ();
-  cairo_matrix_set_affine (matrix, a, b, c, d, 0, 0);
-  i->font = cairo_ft_font_create_for_ft_face (face, FT_LOAD_NO_HINTING,
-					      matrix);
-  cairo_matrix_destroy (matrix);
-  i->next = instance_list;
-  instance_list = i;
-
-  return i->font;
+CairoFont::getFont(void) {
+  return cairo_font;
 }
 
 unsigned long
@@ -357,7 +351,8 @@
 }
 
 CairoFont *
-CairoFontEngine::getFont(GfxFont *gfxFont, XRef *xref) {
+CairoFontEngine::getFont(GfxFont *gfxFont, XRef *xref,
+			 double m11, double m12, double m21, double m22) {
   int i, j;
   Ref ref;
   CairoFont *font;
@@ -371,13 +366,9 @@
 
   ref = *gfxFont->getID();
 
-  font = fontCache[0];
-  if (font && font->matches(ref)) {
-    return font;
-  }
-  for (i = 1; i < cairoFontCacheSize; ++i) {
+  for (i = 0; i < cairoFontCacheSize; ++i) {
     font = fontCache[i];
-    if (font && font->matches(ref)) {
+    if (font && font->matches(ref, m11, m12, m21, m22)) {
       for (j = i; j > 0; --j) {
 	fontCache[j] = fontCache[j-1];
       }
@@ -386,7 +377,7 @@
     }
   }
   
-  font = new CairoFont (gfxFont, xref, lib);
+  font = new CairoFont (gfxFont, xref, lib, m11, m12, m21, m22);
   if (fontCache[cairoFontCacheSize - 1]) {
     delete fontCache[cairoFontCacheSize - 1];
   }

Index: CairoFontEngine.h
===================================================================
RCS file: /cvs/poppler/poppler/poppler/CairoFontEngine.h,v
retrieving revision 1.2
retrieving revision 1.3
diff -u -d -r1.2 -r1.3
--- CairoFontEngine.h	21 Apr 2005 06:35:33 -0000	1.2
+++ CairoFontEngine.h	22 Apr 2005 04:09:23 -0000	1.3
@@ -18,13 +18,13 @@
 
 class CairoFont {
 public:
-  CairoFont(GfxFont *gfxFont, XRef *xref, FT_Library lib);
+  CairoFont(GfxFont *gfxFont, XRef *xref, FT_Library lib,
+	    double m11, double m12, double m21, double m22);
   ~CairoFont();
 
-  GBool matches(Ref &other);
-  cairo_font_t *getFont(double a, double b, double c, double d);
-  unsigned long getGlyph(CharCode code,
-			 Unicode *u, int uLen);
+  GBool matches(Ref &other, double m11, double m12, double m21, double m22);
+  cairo_font_t *getFont(void);
+  unsigned long getGlyph(CharCode code, Unicode *u, int uLen);
   double getSubstitutionCorrection(GfxFont *gfxFont);
 private:
   int substIdx;
@@ -34,18 +34,12 @@
 
   Gushort *codeToGID;
   int codeToGIDLen;
-
-  struct Instance {
-    cairo_font_t *font;
-    double a, b, c, d;
-    Instance *next;
-  };
-  Instance *instance_list;
+  double m11, m12, m21, m22;
 };
 
 //------------------------------------------------------------------------
 
-#define cairoFontCacheSize 16
+#define cairoFontCacheSize 64
 
 //------------------------------------------------------------------------
 // CairoFontEngine
@@ -58,7 +52,8 @@
   CairoFontEngine(FT_Library libA);
   ~CairoFontEngine();
 
-  CairoFont *getFont(GfxFont *gfxFont, XRef *xref);
+  CairoFont *getFont(GfxFont *gfxFont, XRef *xref,
+		     double m11, double m12, double m21, double m22);
 
 private:
   CairoFont *fontCache[cairoFontCacheSize];

Index: CairoOutputDev.cc
===================================================================
RCS file: /cvs/poppler/poppler/poppler/CairoOutputDev.cc,v
retrieving revision 1.6
retrieving revision 1.7
diff -u -d -r1.6 -r1.7
--- CairoOutputDev.cc	21 Apr 2005 06:35:33 -0000	1.6
+++ CairoOutputDev.cc	22 Apr 2005 04:09:23 -0000	1.7
@@ -198,6 +198,7 @@
 
 void CairoOutputDev::updateFont(GfxState *state) {
   cairo_font_t *font;
+  double m11, m12, m21, m22;
   double w;
 
   LOG(printf ("updateFont() font=%s\n", state->getFont()->getName()->getCString()));
@@ -205,21 +206,20 @@
   /* Needs to be rethough, since fonts are now handled by cairo */
   needFontUpdate = gFalse;
 
-  currentFont = fontEngine->getFont (state->getFont(), xref);
-
-  double m11, m12, m21, m22;
-  
   state->getFontTransMat(&m11, &m12, &m21, &m22);
   m11 *= state->getHorizScaling();
   m12 *= state->getHorizScaling();
 
-  LOG(printf ("font matrix: %f %f %f %f\n", m11, m12, m21, m22));
+  /* w = currentFont->getSubstitutionCorrection(state->getFont()); */
+  m12 *= -1;
+  m22 *= -1;
 
-  w = currentFont->getSubstitutionCorrection(state->getFont());
+  LOG(printf ("font matrix: %f %f %f %f\n", m11, m12, m21, m22));
   
-  font = currentFont->getFont(m11, m21, -m12 * w, -m22 * w);
-  if (font)
-    cairo_set_font (cairo, font);
+  currentFont = fontEngine->getFont (state->getFont(), xref,
+				     m11, m21, m12, m22);
+  font = currentFont->getFont();
+  cairo_set_font (cairo, font);
 }
 
 void CairoOutputDev::doPath(GfxState *state, GfxPath *path,



More information about the poppler mailing list