Skip to content

Commit

Permalink
Add a VariableFeatureCompiler
Browse files Browse the repository at this point in the history
This is the same as a FeatureCompiler but it knows its designspace and
it also loads the RulesFeatureWriter if there are any designspace rules
  • Loading branch information
simoncozens committed Jul 19, 2022
1 parent f93228a commit 2159340
Showing 1 changed file with 54 additions and 1 deletion.
55 changes: 54 additions & 1 deletion Lib/ufo2ft/featureCompiler.py
Original file line number Diff line number Diff line change
Expand Up @@ -15,7 +15,10 @@
CursFeatureWriter,
GdefFeatureWriter,
KernFeatureWriter,
VariableKernFeatureWriter,
MarkFeatureWriter,
VariableMarkFeatureWriter,
VariableRulesFeatureWriter,
ast,
isValidFeatureWriter,
loadFeatureWriters,
Expand Down Expand Up @@ -88,6 +91,10 @@ def __init__(self, ufo, ttFont=None, glyphSet=None, **kwargs):

glyphOrder = ttFont.getGlyphOrder()
if glyphSet is not None:
if set(glyphOrder) != set(glyphSet.keys()):
print("Glyph order incompatible")
print("In UFO but not in font:", set(glyphSet.keys()) - set(glyphOrder))
print("In font but not in UFO:", set(glyphOrder) - set(glyphSet.keys()))
assert set(glyphOrder) == set(glyphSet.keys())
else:
glyphSet = ufo
Expand Down Expand Up @@ -210,7 +217,7 @@ def _load_custom_feature_writers(self, featureWriters=None):
if writer is ...:
if seen_ellipsis:
raise ValueError("ellipsis not allowed more than once")
writers = loadFeatureWriters(self.ufo)
writers = loadFeatureWriters(self.ufo, variable=self.designspace)
if writers is not None:
result.extend(writers)
else:
Expand Down Expand Up @@ -324,3 +331,49 @@ def buildTables(self):
table = mtiLib.build(features.splitlines(), self.ttFont)
assert table.tableTag == tag
self.ttFont[tag] = table


class VariableFeatureCompiler(FeatureCompiler):
"""Generate a variable feature file and compile OpenType tables from a
designspace file.
"""

defaultFeatureWriters = [
VariableKernFeatureWriter,
VariableMarkFeatureWriter,
GdefFeatureWriter,
# VariableCursFeatureWriter,
]

def __init__(
self,
ufo,
designspace,
ttFont=None,
glyphSet=None,
featureWriters=None,
**kwargs,
):
self.designspace = designspace
super().__init__(ufo, ttFont, glyphSet, featureWriters, **kwargs)

def setupFeatures(self):
if self.featureWriters:
featureFile = parseLayoutFeatures(self.ufo)

for writer in self.featureWriters:
writer.write(self.designspace, featureFile, compiler=self)

# stringify AST to get correct line numbers in error messages
self.features = featureFile.asFea()
else:
# no featureWriters, simply read existing features' text
self.features = self.ufo.features.text or ""

def initFeatureWriters(self, featureWriters=None):
super().initFeatureWriters(featureWriters)
if self.designspace.rules and not any(
isinstance(writer, VariableRulesFeatureWriter)
for writer in self.featureWriters
):
self.featureWriters = [VariableRulesFeatureWriter()] + self.featureWriters

0 comments on commit 2159340

Please sign in to comment.