aboutsummaryrefslogtreecommitdiff
path: root/Lib/fontTools/merge/layout.py
diff options
context:
space:
mode:
Diffstat (limited to 'Lib/fontTools/merge/layout.py')
-rw-r--r--Lib/fontTools/merge/layout.py776
1 files changed, 420 insertions, 356 deletions
diff --git a/Lib/fontTools/merge/layout.py b/Lib/fontTools/merge/layout.py
index 4bf01c37..6b85cd50 100644
--- a/Lib/fontTools/merge/layout.py
+++ b/Lib/fontTools/merge/layout.py
@@ -14,453 +14,517 @@ log = logging.getLogger("fontTools.merge")
def mergeLookupLists(lst):
- # TODO Do smarter merge.
- return sumLists(lst)
+ # TODO Do smarter merge.
+ return sumLists(lst)
+
def mergeFeatures(lst):
- assert lst
- self = otTables.Feature()
- self.FeatureParams = None
- self.LookupListIndex = mergeLookupLists([l.LookupListIndex for l in lst if l.LookupListIndex])
- self.LookupCount = len(self.LookupListIndex)
- return self
+ assert lst
+ self = otTables.Feature()
+ self.FeatureParams = None
+ self.LookupListIndex = mergeLookupLists(
+ [l.LookupListIndex for l in lst if l.LookupListIndex]
+ )
+ self.LookupCount = len(self.LookupListIndex)
+ return self
+
def mergeFeatureLists(lst):
- d = {}
- for l in lst:
- for f in l:
- tag = f.FeatureTag
- if tag not in d:
- d[tag] = []
- d[tag].append(f.Feature)
- ret = []
- for tag in sorted(d.keys()):
- rec = otTables.FeatureRecord()
- rec.FeatureTag = tag
- rec.Feature = mergeFeatures(d[tag])
- ret.append(rec)
- return ret
+ d = {}
+ for l in lst:
+ for f in l:
+ tag = f.FeatureTag
+ if tag not in d:
+ d[tag] = []
+ d[tag].append(f.Feature)
+ ret = []
+ for tag in sorted(d.keys()):
+ rec = otTables.FeatureRecord()
+ rec.FeatureTag = tag
+ rec.Feature = mergeFeatures(d[tag])
+ ret.append(rec)
+ return ret
+
def mergeLangSyses(lst):
- assert lst
+ assert lst
- # TODO Support merging ReqFeatureIndex
- assert all(l.ReqFeatureIndex == 0xFFFF for l in lst)
+ # TODO Support merging ReqFeatureIndex
+ assert all(l.ReqFeatureIndex == 0xFFFF for l in lst)
+
+ self = otTables.LangSys()
+ self.LookupOrder = None
+ self.ReqFeatureIndex = 0xFFFF
+ self.FeatureIndex = mergeFeatureLists(
+ [l.FeatureIndex for l in lst if l.FeatureIndex]
+ )
+ self.FeatureCount = len(self.FeatureIndex)
+ return self
- self = otTables.LangSys()
- self.LookupOrder = None
- self.ReqFeatureIndex = 0xFFFF
- self.FeatureIndex = mergeFeatureLists([l.FeatureIndex for l in lst if l.FeatureIndex])
- self.FeatureCount = len(self.FeatureIndex)
- return self
def mergeScripts(lst):
- assert lst
-
- if len(lst) == 1:
- return lst[0]
- langSyses = {}
- for sr in lst:
- for lsr in sr.LangSysRecord:
- if lsr.LangSysTag not in langSyses:
- langSyses[lsr.LangSysTag] = []
- langSyses[lsr.LangSysTag].append(lsr.LangSys)
- lsrecords = []
- for tag, langSys_list in sorted(langSyses.items()):
- lsr = otTables.LangSysRecord()
- lsr.LangSys = mergeLangSyses(langSys_list)
- lsr.LangSysTag = tag
- lsrecords.append(lsr)
-
- self = otTables.Script()
- self.LangSysRecord = lsrecords
- self.LangSysCount = len(lsrecords)
- dfltLangSyses = [s.DefaultLangSys for s in lst if s.DefaultLangSys]
- if dfltLangSyses:
- self.DefaultLangSys = mergeLangSyses(dfltLangSyses)
- else:
- self.DefaultLangSys = None
- return self
+ assert lst
+
+ if len(lst) == 1:
+ return lst[0]
+ langSyses = {}
+ for sr in lst:
+ for lsr in sr.LangSysRecord:
+ if lsr.LangSysTag not in langSyses:
+ langSyses[lsr.LangSysTag] = []
+ langSyses[lsr.LangSysTag].append(lsr.LangSys)
+ lsrecords = []
+ for tag, langSys_list in sorted(langSyses.items()):
+ lsr = otTables.LangSysRecord()
+ lsr.LangSys = mergeLangSyses(langSys_list)
+ lsr.LangSysTag = tag
+ lsrecords.append(lsr)
+
+ self = otTables.Script()
+ self.LangSysRecord = lsrecords
+ self.LangSysCount = len(lsrecords)
+ dfltLangSyses = [s.DefaultLangSys for s in lst if s.DefaultLangSys]
+ if dfltLangSyses:
+ self.DefaultLangSys = mergeLangSyses(dfltLangSyses)
+ else:
+ self.DefaultLangSys = None
+ return self
+
def mergeScriptRecords(lst):
- d = {}
- for l in lst:
- for s in l:
- tag = s.ScriptTag
- if tag not in d:
- d[tag] = []
- d[tag].append(s.Script)
- ret = []
- for tag in sorted(d.keys()):
- rec = otTables.ScriptRecord()
- rec.ScriptTag = tag
- rec.Script = mergeScripts(d[tag])
- ret.append(rec)
- return ret
+ d = {}
+ for l in lst:
+ for s in l:
+ tag = s.ScriptTag
+ if tag not in d:
+ d[tag] = []
+ d[tag].append(s.Script)
+ ret = []
+ for tag in sorted(d.keys()):
+ rec = otTables.ScriptRecord()
+ rec.ScriptTag = tag
+ rec.Script = mergeScripts(d[tag])
+ ret.append(rec)
+ return ret
+
otTables.ScriptList.mergeMap = {
- 'ScriptCount': lambda lst: None, # TODO
- 'ScriptRecord': mergeScriptRecords,
+ "ScriptCount": lambda lst: None, # TODO
+ "ScriptRecord": mergeScriptRecords,
}
otTables.BaseScriptList.mergeMap = {
- 'BaseScriptCount': lambda lst: None, # TODO
- # TODO: Merge duplicate entries
- 'BaseScriptRecord': lambda lst: sorted(sumLists(lst), key=lambda s: s.BaseScriptTag),
+ "BaseScriptCount": lambda lst: None, # TODO
+ # TODO: Merge duplicate entries
+ "BaseScriptRecord": lambda lst: sorted(
+ sumLists(lst), key=lambda s: s.BaseScriptTag
+ ),
}
otTables.FeatureList.mergeMap = {
- 'FeatureCount': sum,
- 'FeatureRecord': lambda lst: sorted(sumLists(lst), key=lambda s: s.FeatureTag),
+ "FeatureCount": sum,
+ "FeatureRecord": lambda lst: sorted(sumLists(lst), key=lambda s: s.FeatureTag),
}
otTables.LookupList.mergeMap = {
- 'LookupCount': sum,
- 'Lookup': sumLists,
+ "LookupCount": sum,
+ "Lookup": sumLists,
}
otTables.Coverage.mergeMap = {
- 'Format': min,
- 'glyphs': sumLists,
+ "Format": min,
+ "glyphs": sumLists,
}
otTables.ClassDef.mergeMap = {
- 'Format': min,
- 'classDefs': sumDicts,
+ "Format": min,
+ "classDefs": sumDicts,
}
otTables.LigCaretList.mergeMap = {
- 'Coverage': mergeObjects,
- 'LigGlyphCount': sum,
- 'LigGlyph': sumLists,
+ "Coverage": mergeObjects,
+ "LigGlyphCount": sum,
+ "LigGlyph": sumLists,
}
otTables.AttachList.mergeMap = {
- 'Coverage': mergeObjects,
- 'GlyphCount': sum,
- 'AttachPoint': sumLists,
+ "Coverage": mergeObjects,
+ "GlyphCount": sum,
+ "AttachPoint": sumLists,
}
# XXX Renumber MarkFilterSets of lookups
otTables.MarkGlyphSetsDef.mergeMap = {
- 'MarkSetTableFormat': equal,
- 'MarkSetCount': sum,
- 'Coverage': sumLists,
+ "MarkSetTableFormat": equal,
+ "MarkSetCount": sum,
+ "Coverage": sumLists,
}
otTables.Axis.mergeMap = {
- '*': mergeObjects,
+ "*": mergeObjects,
}
# XXX Fix BASE table merging
otTables.BaseTagList.mergeMap = {
- 'BaseTagCount': sum,
- 'BaselineTag': sumLists,
+ "BaseTagCount": sum,
+ "BaselineTag": sumLists,
}
-otTables.GDEF.mergeMap = \
-otTables.GSUB.mergeMap = \
-otTables.GPOS.mergeMap = \
-otTables.BASE.mergeMap = \
-otTables.JSTF.mergeMap = \
-otTables.MATH.mergeMap = \
-{
- '*': mergeObjects,
- 'Version': max,
+otTables.GDEF.mergeMap = (
+ otTables.GSUB.mergeMap
+) = (
+ otTables.GPOS.mergeMap
+) = otTables.BASE.mergeMap = otTables.JSTF.mergeMap = otTables.MATH.mergeMap = {
+ "*": mergeObjects,
+ "Version": max,
}
-ttLib.getTableClass('GDEF').mergeMap = \
-ttLib.getTableClass('GSUB').mergeMap = \
-ttLib.getTableClass('GPOS').mergeMap = \
-ttLib.getTableClass('BASE').mergeMap = \
-ttLib.getTableClass('JSTF').mergeMap = \
-ttLib.getTableClass('MATH').mergeMap = \
-{
- 'tableTag': onlyExisting(equal), # XXX clean me up
- 'table': mergeObjects,
+ttLib.getTableClass("GDEF").mergeMap = ttLib.getTableClass(
+ "GSUB"
+).mergeMap = ttLib.getTableClass("GPOS").mergeMap = ttLib.getTableClass(
+ "BASE"
+).mergeMap = ttLib.getTableClass(
+ "JSTF"
+).mergeMap = ttLib.getTableClass(
+ "MATH"
+).mergeMap = {
+ "tableTag": onlyExisting(equal), # XXX clean me up
+ "table": mergeObjects,
}
-@add_method(ttLib.getTableClass('GSUB'))
-def merge(self, m, tables):
- assert len(tables) == len(m.duplicateGlyphsPerFont)
- for i,(table,dups) in enumerate(zip(tables, m.duplicateGlyphsPerFont)):
- if not dups: continue
- if table is None or table is NotImplemented:
- log.warning("Have non-identical duplicates to resolve for '%s' but no GSUB. Are duplicates intended?: %s", m.fonts[i]._merger__name, dups)
- continue
-
- synthFeature = None
- synthLookup = None
- for script in table.table.ScriptList.ScriptRecord:
- if script.ScriptTag == 'DFLT': continue # XXX
- for langsys in [script.Script.DefaultLangSys] + [l.LangSys for l in script.Script.LangSysRecord]:
- if langsys is None: continue # XXX Create!
- feature = [v for v in langsys.FeatureIndex if v.FeatureTag == 'locl']
- assert len(feature) <= 1
- if feature:
- feature = feature[0]
- else:
- if not synthFeature:
- synthFeature = otTables.FeatureRecord()
- synthFeature.FeatureTag = 'locl'
- f = synthFeature.Feature = otTables.Feature()
- f.FeatureParams = None
- f.LookupCount = 0
- f.LookupListIndex = []
- table.table.FeatureList.FeatureRecord.append(synthFeature)
- table.table.FeatureList.FeatureCount += 1
- feature = synthFeature
- langsys.FeatureIndex.append(feature)
- langsys.FeatureIndex.sort(key=lambda v: v.FeatureTag)
-
- if not synthLookup:
- subtable = otTables.SingleSubst()
- subtable.mapping = dups
- synthLookup = otTables.Lookup()
- synthLookup.LookupFlag = 0
- synthLookup.LookupType = 1
- synthLookup.SubTableCount = 1
- synthLookup.SubTable = [subtable]
- if table.table.LookupList is None:
- # mtiLib uses None as default value for LookupList,
- # while feaLib points to an empty array with count 0
- # TODO: make them do the same
- table.table.LookupList = otTables.LookupList()
- table.table.LookupList.Lookup = []
- table.table.LookupList.LookupCount = 0
- table.table.LookupList.Lookup.append(synthLookup)
- table.table.LookupList.LookupCount += 1
-
- if feature.Feature.LookupListIndex[:1] != [synthLookup]:
- feature.Feature.LookupListIndex[:0] = [synthLookup]
- feature.Feature.LookupCount += 1
-
- DefaultTable.merge(self, m, tables)
- return self
-
-@add_method(otTables.SingleSubst,
- otTables.MultipleSubst,
- otTables.AlternateSubst,
- otTables.LigatureSubst,
- otTables.ReverseChainSingleSubst,
- otTables.SinglePos,
- otTables.PairPos,
- otTables.CursivePos,
- otTables.MarkBasePos,
- otTables.MarkLigPos,
- otTables.MarkMarkPos)
+@add_method(ttLib.getTableClass("GSUB"))
+def merge(self, m, tables):
+ assert len(tables) == len(m.duplicateGlyphsPerFont)
+ for i, (table, dups) in enumerate(zip(tables, m.duplicateGlyphsPerFont)):
+ if not dups:
+ continue
+ if table is None or table is NotImplemented:
+ log.warning(
+ "Have non-identical duplicates to resolve for '%s' but no GSUB. Are duplicates intended?: %s",
+ m.fonts[i]._merger__name,
+ dups,
+ )
+ continue
+
+ synthFeature = None
+ synthLookup = None
+ for script in table.table.ScriptList.ScriptRecord:
+ if script.ScriptTag == "DFLT":
+ continue # XXX
+ for langsys in [script.Script.DefaultLangSys] + [
+ l.LangSys for l in script.Script.LangSysRecord
+ ]:
+ if langsys is None:
+ continue # XXX Create!
+ feature = [v for v in langsys.FeatureIndex if v.FeatureTag == "locl"]
+ assert len(feature) <= 1
+ if feature:
+ feature = feature[0]
+ else:
+ if not synthFeature:
+ synthFeature = otTables.FeatureRecord()
+ synthFeature.FeatureTag = "locl"
+ f = synthFeature.Feature = otTables.Feature()
+ f.FeatureParams = None
+ f.LookupCount = 0
+ f.LookupListIndex = []
+ table.table.FeatureList.FeatureRecord.append(synthFeature)
+ table.table.FeatureList.FeatureCount += 1
+ feature = synthFeature
+ langsys.FeatureIndex.append(feature)
+ langsys.FeatureIndex.sort(key=lambda v: v.FeatureTag)
+
+ if not synthLookup:
+ subtable = otTables.SingleSubst()
+ subtable.mapping = dups
+ synthLookup = otTables.Lookup()
+ synthLookup.LookupFlag = 0
+ synthLookup.LookupType = 1
+ synthLookup.SubTableCount = 1
+ synthLookup.SubTable = [subtable]
+ if table.table.LookupList is None:
+ # mtiLib uses None as default value for LookupList,
+ # while feaLib points to an empty array with count 0
+ # TODO: make them do the same
+ table.table.LookupList = otTables.LookupList()
+ table.table.LookupList.Lookup = []
+ table.table.LookupList.LookupCount = 0
+ table.table.LookupList.Lookup.append(synthLookup)
+ table.table.LookupList.LookupCount += 1
+
+ if feature.Feature.LookupListIndex[:1] != [synthLookup]:
+ feature.Feature.LookupListIndex[:0] = [synthLookup]
+ feature.Feature.LookupCount += 1
+
+ DefaultTable.merge(self, m, tables)
+ return self
+
+
+@add_method(
+ otTables.SingleSubst,
+ otTables.MultipleSubst,
+ otTables.AlternateSubst,
+ otTables.LigatureSubst,
+ otTables.ReverseChainSingleSubst,
+ otTables.SinglePos,
+ otTables.PairPos,
+ otTables.CursivePos,
+ otTables.MarkBasePos,
+ otTables.MarkLigPos,
+ otTables.MarkMarkPos,
+)
def mapLookups(self, lookupMap):
- pass
+ pass
+
# Copied and trimmed down from subset.py
-@add_method(otTables.ContextSubst,
- otTables.ChainContextSubst,
- otTables.ContextPos,
- otTables.ChainContextPos)
+@add_method(
+ otTables.ContextSubst,
+ otTables.ChainContextSubst,
+ otTables.ContextPos,
+ otTables.ChainContextPos,
+)
def __merge_classify_context(self):
-
- class ContextHelper(object):
- def __init__(self, klass, Format):
- if klass.__name__.endswith('Subst'):
- Typ = 'Sub'
- Type = 'Subst'
- else:
- Typ = 'Pos'
- Type = 'Pos'
- if klass.__name__.startswith('Chain'):
- Chain = 'Chain'
- else:
- Chain = ''
- ChainTyp = Chain+Typ
-
- self.Typ = Typ
- self.Type = Type
- self.Chain = Chain
- self.ChainTyp = ChainTyp
-
- self.LookupRecord = Type+'LookupRecord'
-
- if Format == 1:
- self.Rule = ChainTyp+'Rule'
- self.RuleSet = ChainTyp+'RuleSet'
- elif Format == 2:
- self.Rule = ChainTyp+'ClassRule'
- self.RuleSet = ChainTyp+'ClassSet'
-
- if self.Format not in [1, 2, 3]:
- return None # Don't shoot the messenger; let it go
- if not hasattr(self.__class__, "_merge__ContextHelpers"):
- self.__class__._merge__ContextHelpers = {}
- if self.Format not in self.__class__._merge__ContextHelpers:
- helper = ContextHelper(self.__class__, self.Format)
- self.__class__._merge__ContextHelpers[self.Format] = helper
- return self.__class__._merge__ContextHelpers[self.Format]
-
-
-@add_method(otTables.ContextSubst,
- otTables.ChainContextSubst,
- otTables.ContextPos,
- otTables.ChainContextPos)
+ class ContextHelper(object):
+ def __init__(self, klass, Format):
+ if klass.__name__.endswith("Subst"):
+ Typ = "Sub"
+ Type = "Subst"
+ else:
+ Typ = "Pos"
+ Type = "Pos"
+ if klass.__name__.startswith("Chain"):
+ Chain = "Chain"
+ else:
+ Chain = ""
+ ChainTyp = Chain + Typ
+
+ self.Typ = Typ
+ self.Type = Type
+ self.Chain = Chain
+ self.ChainTyp = ChainTyp
+
+ self.LookupRecord = Type + "LookupRecord"
+
+ if Format == 1:
+ self.Rule = ChainTyp + "Rule"
+ self.RuleSet = ChainTyp + "RuleSet"
+ elif Format == 2:
+ self.Rule = ChainTyp + "ClassRule"
+ self.RuleSet = ChainTyp + "ClassSet"
+
+ if self.Format not in [1, 2, 3]:
+ return None # Don't shoot the messenger; let it go
+ if not hasattr(self.__class__, "_merge__ContextHelpers"):
+ self.__class__._merge__ContextHelpers = {}
+ if self.Format not in self.__class__._merge__ContextHelpers:
+ helper = ContextHelper(self.__class__, self.Format)
+ self.__class__._merge__ContextHelpers[self.Format] = helper
+ return self.__class__._merge__ContextHelpers[self.Format]
+
+
+@add_method(
+ otTables.ContextSubst,
+ otTables.ChainContextSubst,
+ otTables.ContextPos,
+ otTables.ChainContextPos,
+)
def mapLookups(self, lookupMap):
- c = self.__merge_classify_context()
-
- if self.Format in [1, 2]:
- for rs in getattr(self, c.RuleSet):
- if not rs: continue
- for r in getattr(rs, c.Rule):
- if not r: continue
- for ll in getattr(r, c.LookupRecord):
- if not ll: continue
- ll.LookupListIndex = lookupMap[ll.LookupListIndex]
- elif self.Format == 3:
- for ll in getattr(self, c.LookupRecord):
- if not ll: continue
- ll.LookupListIndex = lookupMap[ll.LookupListIndex]
- else:
- assert 0, "unknown format: %s" % self.Format
-
-@add_method(otTables.ExtensionSubst,
- otTables.ExtensionPos)
+ c = self.__merge_classify_context()
+
+ if self.Format in [1, 2]:
+ for rs in getattr(self, c.RuleSet):
+ if not rs:
+ continue
+ for r in getattr(rs, c.Rule):
+ if not r:
+ continue
+ for ll in getattr(r, c.LookupRecord):
+ if not ll:
+ continue
+ ll.LookupListIndex = lookupMap[ll.LookupListIndex]
+ elif self.Format == 3:
+ for ll in getattr(self, c.LookupRecord):
+ if not ll:
+ continue
+ ll.LookupListIndex = lookupMap[ll.LookupListIndex]
+ else:
+ assert 0, "unknown format: %s" % self.Format
+
+
+@add_method(otTables.ExtensionSubst, otTables.ExtensionPos)
def mapLookups(self, lookupMap):
- if self.Format == 1:
- self.ExtSubTable.mapLookups(lookupMap)
- else:
- assert 0, "unknown format: %s" % self.Format
+ if self.Format == 1:
+ self.ExtSubTable.mapLookups(lookupMap)
+ else:
+ assert 0, "unknown format: %s" % self.Format
+
@add_method(otTables.Lookup)
def mapLookups(self, lookupMap):
- for st in self.SubTable:
- if not st: continue
- st.mapLookups(lookupMap)
+ for st in self.SubTable:
+ if not st:
+ continue
+ st.mapLookups(lookupMap)
+
@add_method(otTables.LookupList)
def mapLookups(self, lookupMap):
- for l in self.Lookup:
- if not l: continue
- l.mapLookups(lookupMap)
+ for l in self.Lookup:
+ if not l:
+ continue
+ l.mapLookups(lookupMap)
+
@add_method(otTables.Lookup)
def mapMarkFilteringSets(self, markFilteringSetMap):
- if self.LookupFlag & 0x0010:
- self.MarkFilteringSet = markFilteringSetMap[self.MarkFilteringSet]
+ if self.LookupFlag & 0x0010:
+ self.MarkFilteringSet = markFilteringSetMap[self.MarkFilteringSet]
+
@add_method(otTables.LookupList)
def mapMarkFilteringSets(self, markFilteringSetMap):
- for l in self.Lookup:
- if not l: continue
- l.mapMarkFilteringSets(markFilteringSetMap)
+ for l in self.Lookup:
+ if not l:
+ continue
+ l.mapMarkFilteringSets(markFilteringSetMap)
+
@add_method(otTables.Feature)
def mapLookups(self, lookupMap):
- self.LookupListIndex = [lookupMap[i] for i in self.LookupListIndex]
+ self.LookupListIndex = [lookupMap[i] for i in self.LookupListIndex]
+
@add_method(otTables.FeatureList)
def mapLookups(self, lookupMap):
- for f in self.FeatureRecord:
- if not f or not f.Feature: continue
- f.Feature.mapLookups(lookupMap)
+ for f in self.FeatureRecord:
+ if not f or not f.Feature:
+ continue
+ f.Feature.mapLookups(lookupMap)
+
-@add_method(otTables.DefaultLangSys,
- otTables.LangSys)
+@add_method(otTables.DefaultLangSys, otTables.LangSys)
def mapFeatures(self, featureMap):
- self.FeatureIndex = [featureMap[i] for i in self.FeatureIndex]
- if self.ReqFeatureIndex != 65535:
- self.ReqFeatureIndex = featureMap[self.ReqFeatureIndex]
+ self.FeatureIndex = [featureMap[i] for i in self.FeatureIndex]
+ if self.ReqFeatureIndex != 65535:
+ self.ReqFeatureIndex = featureMap[self.ReqFeatureIndex]
+
@add_method(otTables.Script)
def mapFeatures(self, featureMap):
- if self.DefaultLangSys:
- self.DefaultLangSys.mapFeatures(featureMap)
- for l in self.LangSysRecord:
- if not l or not l.LangSys: continue
- l.LangSys.mapFeatures(featureMap)
+ if self.DefaultLangSys:
+ self.DefaultLangSys.mapFeatures(featureMap)
+ for l in self.LangSysRecord:
+ if not l or not l.LangSys:
+ continue
+ l.LangSys.mapFeatures(featureMap)
+
@add_method(otTables.ScriptList)
def mapFeatures(self, featureMap):
- for s in self.ScriptRecord:
- if not s or not s.Script: continue
- s.Script.mapFeatures(featureMap)
+ for s in self.ScriptRecord:
+ if not s or not s.Script:
+ continue
+ s.Script.mapFeatures(featureMap)
-def layoutPreMerge(font):
- # Map indices to references
-
- GDEF = font.get('GDEF')
- GSUB = font.get('GSUB')
- GPOS = font.get('GPOS')
-
- for t in [GSUB, GPOS]:
- if not t: continue
-
- if t.table.LookupList:
- lookupMap = {i:v for i,v in enumerate(t.table.LookupList.Lookup)}
- t.table.LookupList.mapLookups(lookupMap)
- t.table.FeatureList.mapLookups(lookupMap)
-
- if GDEF and GDEF.table.Version >= 0x00010002:
- markFilteringSetMap = {i:v for i,v in enumerate(GDEF.table.MarkGlyphSetsDef.Coverage)}
- t.table.LookupList.mapMarkFilteringSets(markFilteringSetMap)
-
- if t.table.FeatureList and t.table.ScriptList:
- featureMap = {i:v for i,v in enumerate(t.table.FeatureList.FeatureRecord)}
- t.table.ScriptList.mapFeatures(featureMap)
-
- # TODO FeatureParams nameIDs
-
-def layoutPostMerge(font):
- # Map references back to indices
- GDEF = font.get('GDEF')
- GSUB = font.get('GSUB')
- GPOS = font.get('GPOS')
-
- for t in [GSUB, GPOS]:
- if not t: continue
-
- if t.table.FeatureList and t.table.ScriptList:
-
- # Collect unregistered (new) features.
- featureMap = GregariousIdentityDict(t.table.FeatureList.FeatureRecord)
- t.table.ScriptList.mapFeatures(featureMap)
-
- # Record used features.
- featureMap = AttendanceRecordingIdentityDict(t.table.FeatureList.FeatureRecord)
- t.table.ScriptList.mapFeatures(featureMap)
- usedIndices = featureMap.s
-
- # Remove unused features
- t.table.FeatureList.FeatureRecord = [f for i,f in enumerate(t.table.FeatureList.FeatureRecord) if i in usedIndices]
-
- # Map back to indices.
- featureMap = NonhashableDict(t.table.FeatureList.FeatureRecord)
- t.table.ScriptList.mapFeatures(featureMap)
-
- t.table.FeatureList.FeatureCount = len(t.table.FeatureList.FeatureRecord)
+def layoutPreMerge(font):
+ # Map indices to references
- if t.table.LookupList:
+ GDEF = font.get("GDEF")
+ GSUB = font.get("GSUB")
+ GPOS = font.get("GPOS")
- # Collect unregistered (new) lookups.
- lookupMap = GregariousIdentityDict(t.table.LookupList.Lookup)
- t.table.FeatureList.mapLookups(lookupMap)
- t.table.LookupList.mapLookups(lookupMap)
+ for t in [GSUB, GPOS]:
+ if not t:
+ continue
- # Record used lookups.
- lookupMap = AttendanceRecordingIdentityDict(t.table.LookupList.Lookup)
- t.table.FeatureList.mapLookups(lookupMap)
- t.table.LookupList.mapLookups(lookupMap)
- usedIndices = lookupMap.s
+ if t.table.LookupList:
+ lookupMap = {i: v for i, v in enumerate(t.table.LookupList.Lookup)}
+ t.table.LookupList.mapLookups(lookupMap)
+ t.table.FeatureList.mapLookups(lookupMap)
- # Remove unused lookups
- t.table.LookupList.Lookup = [l for i,l in enumerate(t.table.LookupList.Lookup) if i in usedIndices]
+ if (
+ GDEF
+ and GDEF.table.Version >= 0x00010002
+ and GDEF.table.MarkGlyphSetsDef
+ ):
+ markFilteringSetMap = {
+ i: v for i, v in enumerate(GDEF.table.MarkGlyphSetsDef.Coverage)
+ }
+ t.table.LookupList.mapMarkFilteringSets(markFilteringSetMap)
- # Map back to indices.
- lookupMap = NonhashableDict(t.table.LookupList.Lookup)
- t.table.FeatureList.mapLookups(lookupMap)
- t.table.LookupList.mapLookups(lookupMap)
+ if t.table.FeatureList and t.table.ScriptList:
+ featureMap = {i: v for i, v in enumerate(t.table.FeatureList.FeatureRecord)}
+ t.table.ScriptList.mapFeatures(featureMap)
- t.table.LookupList.LookupCount = len(t.table.LookupList.Lookup)
+ # TODO FeatureParams nameIDs
- if GDEF and GDEF.table.Version >= 0x00010002:
- markFilteringSetMap = NonhashableDict(GDEF.table.MarkGlyphSetsDef.Coverage)
- t.table.LookupList.mapMarkFilteringSets(markFilteringSetMap)
- # TODO FeatureParams nameIDs
+def layoutPostMerge(font):
+ # Map references back to indices
+
+ GDEF = font.get("GDEF")
+ GSUB = font.get("GSUB")
+ GPOS = font.get("GPOS")
+
+ for t in [GSUB, GPOS]:
+ if not t:
+ continue
+
+ if t.table.FeatureList and t.table.ScriptList:
+ # Collect unregistered (new) features.
+ featureMap = GregariousIdentityDict(t.table.FeatureList.FeatureRecord)
+ t.table.ScriptList.mapFeatures(featureMap)
+
+ # Record used features.
+ featureMap = AttendanceRecordingIdentityDict(
+ t.table.FeatureList.FeatureRecord
+ )
+ t.table.ScriptList.mapFeatures(featureMap)
+ usedIndices = featureMap.s
+
+ # Remove unused features
+ t.table.FeatureList.FeatureRecord = [
+ f
+ for i, f in enumerate(t.table.FeatureList.FeatureRecord)
+ if i in usedIndices
+ ]
+
+ # Map back to indices.
+ featureMap = NonhashableDict(t.table.FeatureList.FeatureRecord)
+ t.table.ScriptList.mapFeatures(featureMap)
+
+ t.table.FeatureList.FeatureCount = len(t.table.FeatureList.FeatureRecord)
+
+ if t.table.LookupList:
+ # Collect unregistered (new) lookups.
+ lookupMap = GregariousIdentityDict(t.table.LookupList.Lookup)
+ t.table.FeatureList.mapLookups(lookupMap)
+ t.table.LookupList.mapLookups(lookupMap)
+
+ # Record used lookups.
+ lookupMap = AttendanceRecordingIdentityDict(t.table.LookupList.Lookup)
+ t.table.FeatureList.mapLookups(lookupMap)
+ t.table.LookupList.mapLookups(lookupMap)
+ usedIndices = lookupMap.s
+
+ # Remove unused lookups
+ t.table.LookupList.Lookup = [
+ l for i, l in enumerate(t.table.LookupList.Lookup) if i in usedIndices
+ ]
+
+ # Map back to indices.
+ lookupMap = NonhashableDict(t.table.LookupList.Lookup)
+ t.table.FeatureList.mapLookups(lookupMap)
+ t.table.LookupList.mapLookups(lookupMap)
+
+ t.table.LookupList.LookupCount = len(t.table.LookupList.Lookup)
+
+ if GDEF and GDEF.table.Version >= 0x00010002:
+ markFilteringSetMap = NonhashableDict(
+ GDEF.table.MarkGlyphSetsDef.Coverage
+ )
+ t.table.LookupList.mapMarkFilteringSets(markFilteringSetMap)
+
+ # TODO FeatureParams nameIDs