[feaLib] Support hhea table

This commit is contained in:
Khaled Hosny 2016-04-09 17:42:38 +02:00
parent a61b31a917
commit 5ceaa43d27
6 changed files with 83 additions and 2 deletions

View File

@ -631,3 +631,13 @@ class OS2Field(Statement):
def build(self, builder):
builder.add_os2_field(self.key, self.value)
class HheaField(Statement):
def __init__(self, location, key, value):
Statement.__init__(self, location)
self.key = key
self.value = value
def build(self, builder):
builder.add_hhea_field(self.key, self.value)

View File

@ -69,12 +69,15 @@ class Builder(object):
self.markFilterSets_ = {} # frozenset({"acute", "grave"}) --> 4
# for table 'OS/2'
self.os2_ = {}
# for table 'hhea'
self.hhea_ = {}
def build(self):
self.parseTree = Parser(self.file).parse()
self.parseTree.build(self)
self.build_feature_aalt_()
self.build_head()
self.build_hhea()
self.build_name()
self.build_OS_2()
for tag in ('GPOS', 'GSUB'):
@ -185,6 +188,23 @@ class Builder(object):
table.created = table.modified = 3406620153 # 2011-12-13 11:22:33
table.fontRevision = self.fontRevision_
def build_hhea(self):
if not self.hhea_:
return
table = self.font.get("hhea")
if not table: # this only happens for unit tests
table = self.font["hhea"] = getTableClass("hhea")()
table.decompile(b"\0" * 36, self.font)
table.tableVersion = 1.0
if "caretoffset" in self.hhea_:
table.caretOffset = self.hhea_["caretoffset"]
if "ascender" in self.hhea_:
table.ascent = self.hhea_["ascender"]
if "descender" in self.hhea_:
table.descent = self.hhea_["descender"]
if "linegap" in self.hhea_:
table.lineGap = self.hhea_["linegap"]
def get_user_name_id(self, table):
# Try to find first unused font-specific name id
nameIDs = [name.nameID for name in table.names]
@ -922,6 +942,9 @@ class Builder(object):
def add_os2_field(self, key, value):
self.os2_[key] = value
def add_hhea_field(self, key, value):
self.hhea_[key] = value
def makeOpenTypeAnchor(anchor):
"""ast.Anchor --> otTables.Anchor"""

View File

@ -57,7 +57,7 @@ class BuilderTest(unittest.TestCase):
spec5f_ii_1 spec5f_ii_2 spec5f_ii_3 spec5f_ii_4
spec5h1 spec6b_ii spec6d2 spec6e spec6f
spec6h_ii spec6h_iii_1 spec6h_iii_3d spec8a spec8b spec8c
spec9a spec9b spec9c1 spec9c2 spec9c3 spec9e spec9f
spec9a spec9b spec9c1 spec9c2 spec9c3 spec9d spec9e spec9f
bug453 bug463 bug501 bug502 bug505 bug506 bug509 bug512
name size size2
""".split()
@ -104,7 +104,7 @@ class BuilderTest(unittest.TestCase):
def expect_ttx(self, font, expected_ttx):
path = self.temp_path(suffix=".ttx")
font.saveXML(path, tables=['head', 'name', 'BASE', 'GDEF', 'GSUB',
'GPOS', 'OS/2'])
'GPOS', 'OS/2', 'hhea'])
actual = self.read_ttx(path)
expected = self.read_ttx(expected_ttx)
if actual != expected:

View File

@ -698,6 +698,7 @@ class Parser(object):
handler = {
"GDEF": self.parse_table_GDEF_,
"head": self.parse_table_head_,
"hhea": self.parse_table_hhea_,
"name": self.parse_table_name_,
"BASE": self.parse_table_BASE_,
"OS/2": self.parse_table_OS_2_,
@ -743,6 +744,23 @@ class Parser(object):
raise FeatureLibError("Expected FontRevision",
self.cur_token_location_)
def parse_table_hhea_(self, table):
statements = table.statements
fields = ("CaretOffset", "Ascender", "Descender", "LineGap")
while self.next_token_ != "}":
self.advance_lexer_()
if self.cur_token_type_ is Lexer.NAME and self.cur_token_ in fields:
key = self.cur_token_.lower()
value = self.expect_number_()
statements.append(
ast.HheaField(self.cur_token_location_, key, value))
elif self.cur_token_ == ";":
continue
else:
raise FeatureLibError("Expected CaretOffset, Ascender, "
"Descender or LineGap",
self.cur_token_location_)
def parse_table_name_(self, table):
statements = table.statements
while self.next_token_ != "}":

View File

@ -0,0 +1,6 @@
table hhea {
CaretOffset -50;
Ascender 800;
Descender 200;
LineGap 200;
} hhea;

View File

@ -0,0 +1,24 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont>
<hhea>
<tableVersion value="1.0"/>
<ascent value="800"/>
<descent value="200"/>
<lineGap value="200"/>
<advanceWidthMax value="0"/>
<minLeftSideBearing value="0"/>
<minRightSideBearing value="0"/>
<xMaxExtent value="0"/>
<caretSlopeRise value="0"/>
<caretSlopeRun value="0"/>
<caretOffset value="-50"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="0"/>
</hhea>
</ttFont>