Commit a1e85f11c8e074eafb68875b9c9b88316d9aa55a

Werner Lemberg 2016-12-20T10:52:26

[cff, truetype] Fast advance width retrieval for fonts with HVAR. Everything is guarded with TT_CONFIG_OPTION_GX_VAR_SUPPORT. * src/base/ftadvanc.c (LOAD_ADVANCE_FAST_CHECK): Don't handle MM. * src/cff/cffdrivr.c: Include FT_SERVICE_METRICS_VARIATIONS_H. (cff_get_advances): Test for HVAR and VVAR. * src/truetype/ttdriver.c (tt_get_advances): Test for HVAR and VVAR.

diff --git a/ChangeLog b/ChangeLog
index 5221d9d..11c9d80 100644
--- a/ChangeLog
+++ b/ChangeLog
@@ -1,3 +1,16 @@
+2016-12-20  Werner Lemberg  <wl@gnu.org>
+
+	[cff, truetype] Fast advance width retrieval for fonts with HVAR.
+
+	Everything is guarded with TT_CONFIG_OPTION_GX_VAR_SUPPORT.
+
+	* src/base/ftadvanc.c (LOAD_ADVANCE_FAST_CHECK): Don't handle MM.
+
+	* src/cff/cffdrivr.c: Include FT_SERVICE_METRICS_VARIATIONS_H.
+	(cff_get_advances): Test for HVAR and VVAR.
+
+	* src/truetype/ttdriver.c (tt_get_advances): Test for HVAR and VVAR.
+
 2016-12-18  Werner Lemberg  <wl@gnu.org>
 
 	[base] Fix invalid mac font recursion.
diff --git a/src/base/ftadvanc.c b/src/base/ftadvanc.c
index 9e2ab89..31a2c04 100644
--- a/src/base/ftadvanc.c
+++ b/src/base/ftadvanc.c
@@ -60,12 +60,13 @@
    /*  - unscaled load                                             */
    /*  - unhinted load                                             */
    /*  - light-hinted load                                         */
-   /*  - neither a MM nor a GX font                                */
+   /*  - if a variations font, it must have an `HVAR' or `VVAR'    */
+   /*    table (thus the old MM or GX fonts don't qualify; this    */
+   /*    gets checked by the driver-specific functions)            */
 
-#define LOAD_ADVANCE_FAST_CHECK( face, flags )                          \
-          ( ( flags & ( FT_LOAD_NO_SCALE | FT_LOAD_NO_HINTING )    ||   \
-              FT_LOAD_TARGET_MODE( flags ) == FT_RENDER_MODE_LIGHT ) && \
-            !FT_HAS_MULTIPLE_MASTERS( face )                         )
+#define LOAD_ADVANCE_FAST_CHECK( face, flags )                      \
+          ( flags & ( FT_LOAD_NO_SCALE | FT_LOAD_NO_HINTING )    || \
+            FT_LOAD_TARGET_MODE( flags ) == FT_RENDER_MODE_LIGHT )
 
 
   /* documentation is in ftadvanc.h */
diff --git a/src/cff/cffdrivr.c b/src/cff/cffdrivr.c
index c6d228f..3e0ef86 100644
--- a/src/cff/cffdrivr.c
+++ b/src/cff/cffdrivr.c
@@ -34,6 +34,7 @@
 
 #ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
 #include FT_SERVICE_MULTIPLE_MASTERS_H
+#include FT_SERVICE_METRICS_VARIATIONS_H
 #endif
 
 #include "cfferrs.h"
@@ -208,9 +209,21 @@
       TT_Face   ttface = (TT_Face)face;
       FT_Short  dummy;
 
+#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
+      FT_Service_MetricsVariations  var =
+        (FT_Service_MetricsVariations)ttface->var;
+#endif
+
 
       if ( flags & FT_LOAD_VERTICAL_LAYOUT )
       {
+#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
+        /* no fast retrieval for blended MM fonts without VVAR table */
+        if ( ( FT_HAS_MULTIPLE_MASTERS( face ) && ttface->blend ) &&
+             !( var && var->vadvance_adjust )                     )
+          return FT_THROW( Unimplemented_Feature );
+#endif
+
         /* check whether we have data from the `vmtx' table at all; */
         /* otherwise we extract the info from the CFF glyphstrings  */
         /* (instead of synthesizing a global value using the `OS/2' */
@@ -236,6 +249,13 @@
       }
       else
       {
+#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
+        /* no fast retrieval for blended MM fonts without HVAR table */
+        if ( ( FT_HAS_MULTIPLE_MASTERS( face ) && ttface->blend ) &&
+             !( var && var->hadvance_adjust )                     )
+          return FT_THROW( Unimplemented_Feature );
+#endif
+
         /* check whether we have data from the `hmtx' table at all */
         if ( !ttface->horizontal.number_Of_HMetrics )
           goto Missing_Table;
diff --git a/src/truetype/ttdriver.c b/src/truetype/ttdriver.c
index 93385a5..66e721e 100644
--- a/src/truetype/ttdriver.c
+++ b/src/truetype/ttdriver.c
@@ -224,13 +224,25 @@
                    FT_Fixed  *advances )
   {
     FT_UInt  nn;
-    TT_Face  face = (TT_Face) ttface;
+    TT_Face  face = (TT_Face)ttface;
+
+#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
+    FT_Service_MetricsVariations  var =
+      (FT_Service_MetricsVariations)face->var;
+#endif
 
 
     /* XXX: TODO: check for sbits */
 
     if ( flags & FT_LOAD_VERTICAL_LAYOUT )
     {
+#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
+      /* no fast retrieval for blended MM fonts without VVAR table */
+      if ( ( FT_HAS_MULTIPLE_MASTERS( ttface ) && face->blend ) &&
+           !( var && var->vadvance_adjust )                     )
+        return FT_THROW( Unimplemented_Feature );
+#endif
+
       for ( nn = 0; nn < count; nn++ )
       {
         FT_Short   tsb;
@@ -244,6 +256,13 @@
     }
     else
     {
+#ifdef TT_CONFIG_OPTION_GX_VAR_SUPPORT
+      /* no fast retrieval for blended MM fonts without HVAR table */
+      if ( ( FT_HAS_MULTIPLE_MASTERS( ttface ) && face->blend ) &&
+           !( var && var->hadvance_adjust )                     )
+        return FT_THROW( Unimplemented_Feature );
+#endif
+
       for ( nn = 0; nn < count; nn++ )
       {
         FT_Short   lsb;