summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJames Godfrey-Kittle <jamesgk@google.com>2015-01-30 17:26:03 -0800
committerJames Godfrey-Kittle <jamesgk@google.com>2015-04-16 12:16:27 -0700
commit47f22b2367b0d8c9b47ec73d974e9b4765bb0986 (patch)
tree413bfa44a15f255d27d08fa2c6a751e61e2060eb
parente014eabf404f2d7789cb93e9208c9fdb2313b316 (diff)
Add OTF generation using ufo2fdk
-rw-r--r--scripts/build-v2.py5
-rw-r--r--scripts/lib/fontbuild/Build.py31
-rw-r--r--scripts/lib/fontbuild/saveOTF.py62
3 files changed, 86 insertions, 12 deletions
diff --git a/scripts/build-v2.py b/scripts/build-v2.py
index e1fdf78..b21a8b4 100644
--- a/scripts/build-v2.py
+++ b/scripts/build-v2.py
@@ -60,8 +60,11 @@ proj.incrementBuildNumber()
# FAMILYNAME = "Roboto2"
FAMILYNAME = "Roboto"
+proj.buildOTF = True
'''
-proj.buldVFBandFEA = True
+proj.checkOTFOutlines = True
+proj.autohintOTF = True
+proj.buildFEA = True
'''
proj.generateFont(th.font,"%s/Thin/Regular/Th"%FAMILYNAME)
proj.generateFont(Mix([th,rg], 0.45),"%s/Light/Regular/Lt"%FAMILYNAME)
diff --git a/scripts/lib/fontbuild/Build.py b/scripts/lib/fontbuild/Build.py
index ed5eed5..c4e8450 100644
--- a/scripts/lib/fontbuild/Build.py
+++ b/scripts/lib/fontbuild/Build.py
@@ -1,3 +1,4 @@
+from robofab.world import OpenFont
from fontbuild.mix import Mix,Master,narrowFLGlyph
from fontbuild.instanceNames import setNamesRF
from fontbuild.italics import italicizeGlyph
@@ -11,6 +12,7 @@ from fontbuild.markFeature import GenerateFeature_mark
from fontbuild.mkmkFeature import GenerateFeature_mkmk
from fontbuild.decomposeGlyph import decomposeGlyph
from fontbuild.removeGlyphOverlap import removeGlyphOverlap
+from fontbuild.saveOTF import saveOTF
from fontbuild.sortGlyphs import sortGlyphsByUnicode
import ConfigParser
import os
@@ -39,7 +41,10 @@ class FontProject:
self.deleteList = self.config.get("glyphs","delete").split()
self.buildnumber = self.loadBuildNumber()
- self.buldVFBandFEA = False
+ self.buildOTF = False
+ self.checkOTFOutlines = False
+ self.autohintOTF = False
+ self.buildFEA = False
def loadBuildNumber(self):
@@ -153,22 +158,25 @@ class FontProject:
fontName = "%s-%s" % (f.info.familyName.replace(" ", ""),
f.info.styleName.replace(" ", ""))
- if self.buldVFBandFEA:
- log(">> Generating VFB files")
- directoryPath = "%s/%s/%sVFB"%(self.basedir,self.builddir,directoryName)
- if not os.path.exists(directoryPath):
- os.makedirs(directoryPath)
- flName = "%s/%s.vfb"%(directoryPath,f.font_name)
- fl.GenerateFont(fl.ifont,ftFONTLAB,flName)
-
log(">> Generating font files")
- directoryPath = "%s/%s/%sTTF"%(self.basedir,self.builddir,directoryName)
+ directoryPath = "%s/%s/%sUFO"%(self.basedir,self.builddir,directoryName)
if not os.path.exists(directoryPath):
os.makedirs(directoryPath)
ufoName = "%s/%s.ufo" % (directoryPath, fontName)
f.save(ufoName)
- if self.buldVFBandFEA:
+ if self.buildOTF:
+ log(">> Generating OTF file")
+ newFont = OpenFont(ufoName)
+ directoryPath = "%s/%s/%sOTF" % (self.basedir, self.builddir,
+ directoryName)
+ if not os.path.exists(directoryPath):
+ os.makedirs(directoryPath)
+ otfName = "%s/%s.otf" % (directoryPath, fontName)
+ saveOTF(newFont, otfName, checkOutlines=self.checkOTFOutlines,
+ autohint=self.autohintOTF)
+
+ if self.buildFEA:
log(">> Generating FEA files")
GenerateFeature_mark(f)
GenerateFeature_mkmk(f)
@@ -232,6 +240,7 @@ def generateGlyphs(f, glyphNames):
generateGlyph(f, glyphName)
def cleanCurves(f):
+ #TODO(jamesgk) remove calls to removeGlyphOverlap if we decide to use AFDKO
log(">> Removing overlaps")
for g in f:
removeGlyphOverlap(g)
diff --git a/scripts/lib/fontbuild/saveOTF.py b/scripts/lib/fontbuild/saveOTF.py
new file mode 100644
index 0000000..b2a6483
--- /dev/null
+++ b/scripts/lib/fontbuild/saveOTF.py
@@ -0,0 +1,62 @@
+import re
+from fontTools.ttLib import newTable
+from fontTools.ttLib.tables._c_m_a_p import cmap_format_12
+from ufo2fdk import OTFCompiler
+from ufo2fdk.makeotfParts import MakeOTFPartsCompiler
+from ufo2fdk.outlineOTF import OutlineOTFCompiler
+
+
+def saveOTF(font, destFile, checkOutlines=False, autohint=False):
+ """Save a RoboFab font as an OTF binary using ufo2fdk."""
+
+ # according to the AGL spec, names of glyphs outside the BMP must have
+ # prefix "u" and not "uni": http://sourceforge.net/adobe/aglfn/aglspec
+ for glyph in font:
+ glyph.name = re.sub(r"uni([\dA-F]{5,})", r"u\1", glyph.name)
+
+ compiler = OTFCompiler(partsCompilerClass=_PartsCompilerBlankGlyphOrder,
+ outlineCompilerClass=_OutlineCompilerFormat12)
+ reports = compiler.compile(font, destFile, checkOutlines=checkOutlines,
+ autohint=autohint)
+ if checkOutlines:
+ print reports["checkOutlines"]
+ if autohint:
+ print reports["autohint"]
+ print reports["makeotf"]
+
+
+class _PartsCompilerBlankGlyphOrder(MakeOTFPartsCompiler):
+ """Child class of parts compiler which produces a blank glyph order file.
+
+ This seems necessary for now because AFDKO's makeotf function produces
+ Roboto OTFs without ASCII mappings when called with ufo2fdk's default glyph
+ order file.
+ """
+
+ def setupFile_glyphOrder(self, path):
+ f = open(path, "w")
+ f.close()
+
+
+class _OutlineCompilerFormat12(OutlineOTFCompiler):
+ """Child class of outline compiler to work with format 12 cmaps."""
+
+ def setupTable_cmap(self):
+ """Set up cmap exactly like ufo2fdk, switching format 4 for 12."""
+
+ # set up a mac-compatible table
+ cmap12_0_3 = cmap_format_12(12)
+ cmap12_0_3.platformID = 0
+ cmap12_0_3.platEncID = 3
+ cmap12_0_3.language = 0
+ cmap12_0_3.cmap = dict(self.unicodeToGlyphNameMapping)
+ # set up a windows-compatible table
+ cmap12_3_1 = cmap_format_12(12)
+ cmap12_3_1.platformID = 3
+ cmap12_3_1.platEncID = 1
+ cmap12_3_1.language = 0
+ cmap12_3_1.cmap = dict(self.unicodeToGlyphNameMapping)
+ # store the tables in the cmap
+ self.otf["cmap"] = cmap = newTable("cmap")
+ cmap.tableVersion = 0
+ cmap.tables = [cmap12_0_3, cmap12_3_1]