Merge remote-tracking branch 'origin/master' into partial-instancer

This commit is contained in:
Cosimo Lupo 2019-06-18 18:45:47 +01:00
commit 6f1d25497a
No known key found for this signature in database
GPG Key ID: 20D4A261E4A0E642
30 changed files with 4221 additions and 379 deletions

View File

@ -5,6 +5,6 @@ from fontTools.misc.loggingTools import configLogger
log = logging.getLogger(__name__) log = logging.getLogger(__name__)
version = __version__ = "3.42.1.dev0" version = __version__ = "3.43.1.dev0"
__all__ = ["version", "log", "configLogger"] __all__ = ["version", "log", "configLogger"]

View File

@ -1,4 +1,5 @@
from __future__ import print_function, division, absolute_import from __future__ import print_function, division, absolute_import
from collections import namedtuple
from fontTools import ttLib from fontTools import ttLib
from fontTools.ttLib.tables import otTables as ot from fontTools.ttLib.tables import otTables as ot
from fontTools.ttLib.tables.otBase import ValueRecord, valueRecordFormatDict from fontTools.ttLib.tables.otBase import ValueRecord, valueRecordFormatDict
@ -488,17 +489,25 @@ def _getSinglePosValueKey(valueRecord):
return tuple(result) return tuple(result)
_DeviceTuple = namedtuple("_DeviceTuple", "DeltaFormat StartSize EndSize DeltaValue")
def _makeDeviceTuple(device): def _makeDeviceTuple(device):
"""otTables.Device --> tuple, for making device tables unique""" """otTables.Device --> tuple, for making device tables unique"""
return (device.DeltaFormat, device.StartSize, device.EndSize, return _DeviceTuple(
tuple(device.DeltaValue)) device.DeltaFormat,
device.StartSize,
device.EndSize,
() if device.DeltaFormat & 0x8000 else tuple(device.DeltaValue)
)
def _getSinglePosValueSize(valueKey): def _getSinglePosValueSize(valueKey):
"""Returns how many ushorts this valueKey (short form of ValueRecord) takes up""" """Returns how many ushorts this valueKey (short form of ValueRecord) takes up"""
count = 0 count = 0
for k in valueKey[1:]: for _, v in valueKey[1:]:
if hasattr(k[1], '__len__') and len(k[1]): if isinstance(v, _DeviceTuple):
count += len(k[1][3]) + 3 count += len(v.DeltaValue) + 3
else: else:
count += 1 count += 1
return count return count

View File

@ -16,7 +16,7 @@ from fontTools.ttLib.tables import ttProgram
import logging import logging
log = logging.getLogger(__name__) log = logging.getLogger("fontTools.ttLib.woff2")
haveBrotli = False haveBrotli = False
try: try:
@ -82,7 +82,7 @@ class WOFF2Reader(SFNTReader):
"""Fetch the raw table data. Reconstruct transformed tables.""" """Fetch the raw table data. Reconstruct transformed tables."""
entry = self.tables[Tag(tag)] entry = self.tables[Tag(tag)]
if not hasattr(entry, 'data'): if not hasattr(entry, 'data'):
if tag in woff2TransformedTableTags: if entry.transformed:
entry.data = self.reconstructTable(tag) entry.data = self.reconstructTable(tag)
else: else:
entry.data = entry.loadData(self.transformBuffer) entry.data = entry.loadData(self.transformBuffer)
@ -90,8 +90,6 @@ class WOFF2Reader(SFNTReader):
def reconstructTable(self, tag): def reconstructTable(self, tag):
"""Reconstruct table named 'tag' from transformed data.""" """Reconstruct table named 'tag' from transformed data."""
if tag not in woff2TransformedTableTags:
raise TTLibError("transform for table '%s' is unknown" % tag)
entry = self.tables[Tag(tag)] entry = self.tables[Tag(tag)]
rawData = entry.loadData(self.transformBuffer) rawData = entry.loadData(self.transformBuffer)
if tag == 'glyf': if tag == 'glyf':
@ -100,8 +98,10 @@ class WOFF2Reader(SFNTReader):
data = self._reconstructGlyf(rawData, padding) data = self._reconstructGlyf(rawData, padding)
elif tag == 'loca': elif tag == 'loca':
data = self._reconstructLoca() data = self._reconstructLoca()
elif tag == 'hmtx':
data = self._reconstructHmtx(rawData)
else: else:
raise NotImplementedError raise TTLibError("transform for table '%s' is unknown" % tag)
return data return data
def _reconstructGlyf(self, data, padding=None): def _reconstructGlyf(self, data, padding=None):
@ -130,6 +130,34 @@ class WOFF2Reader(SFNTReader):
% (self.tables['loca'].origLength, len(data))) % (self.tables['loca'].origLength, len(data)))
return data return data
def _reconstructHmtx(self, data):
""" Return reconstructed hmtx table data. """
# Before reconstructing 'hmtx' table we need to parse other tables:
# 'glyf' is required for reconstructing the sidebearings from the glyphs'
# bounding box; 'hhea' is needed for the numberOfHMetrics field.
if "glyf" in self.flavorData.transformedTables:
# transformed 'glyf' table is self-contained, thus 'loca' not needed
tableDependencies = ("maxp", "hhea", "glyf")
else:
# decompiling untransformed 'glyf' requires 'loca', which requires 'head'
tableDependencies = ("maxp", "head", "hhea", "loca", "glyf")
for tag in tableDependencies:
self._decompileTable(tag)
hmtxTable = self.ttFont["hmtx"] = WOFF2HmtxTable()
hmtxTable.reconstruct(data, self.ttFont)
data = hmtxTable.compile(self.ttFont)
return data
def _decompileTable(self, tag):
"""Decompile table data and store it inside self.ttFont."""
data = self[tag]
if self.ttFont.isLoaded(tag):
return self.ttFont[tag]
tableClass = getTableClass(tag)
table = tableClass(tag)
self.ttFont.tables[tag] = table
table.decompile(data, self.ttFont)
class WOFF2Writer(SFNTWriter): class WOFF2Writer(SFNTWriter):
@ -199,7 +227,7 @@ class WOFF2Writer(SFNTWriter):
# See: # See:
# https://github.com/khaledhosny/ots/issues/60 # https://github.com/khaledhosny/ots/issues/60
# https://github.com/google/woff2/issues/15 # https://github.com/google/woff2/issues/15
if isTrueType: if isTrueType and "glyf" in self.flavorData.transformedTables:
self._normaliseGlyfAndLoca(padding=4) self._normaliseGlyfAndLoca(padding=4)
self._setHeadTransformFlag() self._setHeadTransformFlag()
@ -234,13 +262,7 @@ class WOFF2Writer(SFNTWriter):
if self.sfntVersion == "OTTO": if self.sfntVersion == "OTTO":
return return
# make up glyph names required to decompile glyf table for tag in ('maxp', 'head', 'loca', 'glyf'):
self._decompileTable('maxp')
numGlyphs = self.ttFont['maxp'].numGlyphs
glyphOrder = ['.notdef'] + ["glyph%.5d" % i for i in range(1, numGlyphs)]
self.ttFont.setGlyphOrder(glyphOrder)
for tag in ('head', 'loca', 'glyf'):
self._decompileTable(tag) self._decompileTable(tag)
self.ttFont['glyf'].padding = padding self.ttFont['glyf'].padding = padding
for tag in ('glyf', 'loca'): for tag in ('glyf', 'loca'):
@ -265,6 +287,8 @@ class WOFF2Writer(SFNTWriter):
tableClass = WOFF2LocaTable tableClass = WOFF2LocaTable
elif tag == 'glyf': elif tag == 'glyf':
tableClass = WOFF2GlyfTable tableClass = WOFF2GlyfTable
elif tag == 'hmtx':
tableClass = WOFF2HmtxTable
else: else:
tableClass = getTableClass(tag) tableClass = getTableClass(tag)
table = tableClass(tag) table = tableClass(tag)
@ -293,11 +317,17 @@ class WOFF2Writer(SFNTWriter):
def _transformTables(self): def _transformTables(self):
"""Return transformed font data.""" """Return transformed font data."""
transformedTables = self.flavorData.transformedTables
for tag, entry in self.tables.items(): for tag, entry in self.tables.items():
if tag in woff2TransformedTableTags: data = None
if tag in transformedTables:
data = self.transformTable(tag) data = self.transformTable(tag)
else: if data is not None:
entry.transformed = True
if data is None:
# pass-through the table data without transformation
data = entry.data data = entry.data
entry.transformed = False
entry.offset = self.nextTableOffset entry.offset = self.nextTableOffset
entry.saveData(self.transformBuffer, data) entry.saveData(self.transformBuffer, data)
self.nextTableOffset += entry.length self.nextTableOffset += entry.length
@ -306,9 +336,9 @@ class WOFF2Writer(SFNTWriter):
return fontData return fontData
def transformTable(self, tag): def transformTable(self, tag):
"""Return transformed table data.""" """Return transformed table data, or None if some pre-conditions aren't
if tag not in woff2TransformedTableTags: met -- in which case, the non-transformed table data will be used.
raise TTLibError("Transform for table '%s' is unknown" % tag) """
if tag == "loca": if tag == "loca":
data = b"" data = b""
elif tag == "glyf": elif tag == "glyf":
@ -316,8 +346,15 @@ class WOFF2Writer(SFNTWriter):
self._decompileTable(tag) self._decompileTable(tag)
glyfTable = self.ttFont['glyf'] glyfTable = self.ttFont['glyf']
data = glyfTable.transform(self.ttFont) data = glyfTable.transform(self.ttFont)
elif tag == "hmtx":
if "glyf" not in self.tables:
return
for tag in ("maxp", "head", "hhea", "loca", "glyf", "hmtx"):
self._decompileTable(tag)
hmtxTable = self.ttFont["hmtx"]
data = hmtxTable.transform(self.ttFont) # can be None
else: else:
raise NotImplementedError raise TTLibError("Transform for table '%s' is unknown" % tag)
return data return data
def _calcMasterChecksum(self): def _calcMasterChecksum(self):
@ -533,11 +570,9 @@ class WOFF2DirectoryEntry(DirectoryEntry):
# otherwise, tag is derived from a fixed 'Known Tags' table # otherwise, tag is derived from a fixed 'Known Tags' table
self.tag = woff2KnownTags[self.flags & 0x3F] self.tag = woff2KnownTags[self.flags & 0x3F]
self.tag = Tag(self.tag) self.tag = Tag(self.tag)
if self.flags & 0xC0 != 0:
raise TTLibError('bits 6-7 are reserved and must be 0')
self.origLength, data = unpackBase128(data) self.origLength, data = unpackBase128(data)
self.length = self.origLength self.length = self.origLength
if self.tag in woff2TransformedTableTags: if self.transformed:
self.length, data = unpackBase128(data) self.length, data = unpackBase128(data)
if self.tag == 'loca' and self.length != 0: if self.tag == 'loca' and self.length != 0:
raise TTLibError( raise TTLibError(
@ -550,10 +585,44 @@ class WOFF2DirectoryEntry(DirectoryEntry):
if (self.flags & 0x3F) == 0x3F: if (self.flags & 0x3F) == 0x3F:
data += struct.pack('>4s', self.tag.tobytes()) data += struct.pack('>4s', self.tag.tobytes())
data += packBase128(self.origLength) data += packBase128(self.origLength)
if self.tag in woff2TransformedTableTags: if self.transformed:
data += packBase128(self.length) data += packBase128(self.length)
return data return data
@property
def transformVersion(self):
"""Return bits 6-7 of table entry's flags, which indicate the preprocessing
transformation version number (between 0 and 3).
"""
return self.flags >> 6
@transformVersion.setter
def transformVersion(self, value):
assert 0 <= value <= 3
self.flags |= value << 6
@property
def transformed(self):
"""Return True if the table has any transformation, else return False."""
# For all tables in a font, except for 'glyf' and 'loca', the transformation
# version 0 indicates the null transform (where the original table data is
# passed directly to the Brotli compressor). For 'glyf' and 'loca' tables,
# transformation version 3 indicates the null transform
if self.tag in {"glyf", "loca"}:
return self.transformVersion != 3
else:
return self.transformVersion != 0
@transformed.setter
def transformed(self, booleanValue):
# here we assume that a non-null transform means version 0 for 'glyf' and
# 'loca' and 1 for every other table (e.g. hmtx); but that may change as
# new transformation formats are introduced in the future (if ever).
if self.tag in {"glyf", "loca"}:
self.transformVersion = 3 if not booleanValue else 0
else:
self.transformVersion = int(booleanValue)
class WOFF2LocaTable(getTableClass('loca')): class WOFF2LocaTable(getTableClass('loca')):
"""Same as parent class. The only difference is that it attempts to preserve """Same as parent class. The only difference is that it attempts to preserve
@ -652,19 +721,7 @@ class WOFF2GlyfTable(getTableClass('glyf')):
def transform(self, ttFont): def transform(self, ttFont):
""" Return transformed 'glyf' data """ """ Return transformed 'glyf' data """
self.numGlyphs = len(self.glyphs) self.numGlyphs = len(self.glyphs)
if not hasattr(self, "glyphOrder"): assert len(self.glyphOrder) == self.numGlyphs
try:
self.glyphOrder = ttFont.getGlyphOrder()
except:
self.glyphOrder = None
if self.glyphOrder is None:
self.glyphOrder = [".notdef"]
self.glyphOrder.extend(["glyph%.5d" % i for i in range(1, self.numGlyphs)])
if len(self.glyphOrder) != self.numGlyphs:
raise TTLibError(
"incorrect glyphOrder: expected %d glyphs, found %d" %
(len(self.glyphOrder), self.numGlyphs))
if 'maxp' in ttFont: if 'maxp' in ttFont:
ttFont['maxp'].numGlyphs = self.numGlyphs ttFont['maxp'].numGlyphs = self.numGlyphs
self.indexFormat = ttFont['head'].indexToLocFormat self.indexFormat = ttFont['head'].indexToLocFormat
@ -909,13 +966,193 @@ class WOFF2GlyfTable(getTableClass('glyf')):
self.glyphStream += triplets.tostring() self.glyphStream += triplets.tostring()
class WOFF2HmtxTable(getTableClass("hmtx")):
def __init__(self, tag=None):
self.tableTag = Tag(tag or 'hmtx')
def reconstruct(self, data, ttFont):
flags, = struct.unpack(">B", data[:1])
data = data[1:]
if flags & 0b11111100 != 0:
raise TTLibError("Bits 2-7 of '%s' flags are reserved" % self.tableTag)
# When bit 0 is _not_ set, the lsb[] array is present
hasLsbArray = flags & 1 == 0
# When bit 1 is _not_ set, the leftSideBearing[] array is present
hasLeftSideBearingArray = flags & 2 == 0
if hasLsbArray and hasLeftSideBearingArray:
raise TTLibError(
"either bits 0 or 1 (or both) must set in transformed '%s' flags"
% self.tableTag
)
glyfTable = ttFont["glyf"]
headerTable = ttFont["hhea"]
glyphOrder = glyfTable.glyphOrder
numGlyphs = len(glyphOrder)
numberOfHMetrics = min(int(headerTable.numberOfHMetrics), numGlyphs)
assert len(data) >= 2 * numberOfHMetrics
advanceWidthArray = array.array("H", data[:2 * numberOfHMetrics])
if sys.byteorder != "big":
advanceWidthArray.byteswap()
data = data[2 * numberOfHMetrics:]
if hasLsbArray:
assert len(data) >= 2 * numberOfHMetrics
lsbArray = array.array("h", data[:2 * numberOfHMetrics])
if sys.byteorder != "big":
lsbArray.byteswap()
data = data[2 * numberOfHMetrics:]
else:
# compute (proportional) glyphs' lsb from their xMin
lsbArray = array.array("h")
for i, glyphName in enumerate(glyphOrder):
if i >= numberOfHMetrics:
break
glyph = glyfTable[glyphName]
xMin = getattr(glyph, "xMin", 0)
lsbArray.append(xMin)
numberOfSideBearings = numGlyphs - numberOfHMetrics
if hasLeftSideBearingArray:
assert len(data) >= 2 * numberOfSideBearings
leftSideBearingArray = array.array("h", data[:2 * numberOfSideBearings])
if sys.byteorder != "big":
leftSideBearingArray.byteswap()
data = data[2 * numberOfSideBearings:]
else:
# compute (monospaced) glyphs' leftSideBearing from their xMin
leftSideBearingArray = array.array("h")
for i, glyphName in enumerate(glyphOrder):
if i < numberOfHMetrics:
continue
glyph = glyfTable[glyphName]
xMin = getattr(glyph, "xMin", 0)
leftSideBearingArray.append(xMin)
if data:
raise TTLibError("too much '%s' table data" % self.tableTag)
self.metrics = {}
for i in range(numberOfHMetrics):
glyphName = glyphOrder[i]
advanceWidth, lsb = advanceWidthArray[i], lsbArray[i]
self.metrics[glyphName] = (advanceWidth, lsb)
lastAdvance = advanceWidthArray[-1]
for i in range(numberOfSideBearings):
glyphName = glyphOrder[i + numberOfHMetrics]
self.metrics[glyphName] = (lastAdvance, leftSideBearingArray[i])
def transform(self, ttFont):
glyphOrder = ttFont.getGlyphOrder()
glyf = ttFont["glyf"]
hhea = ttFont["hhea"]
numberOfHMetrics = hhea.numberOfHMetrics
# check if any of the proportional glyphs has left sidebearings that
# differ from their xMin bounding box values.
hasLsbArray = False
for i in range(numberOfHMetrics):
glyphName = glyphOrder[i]
lsb = self.metrics[glyphName][1]
if lsb != getattr(glyf[glyphName], "xMin", 0):
hasLsbArray = True
break
# do the same for the monospaced glyphs (if any) at the end of hmtx table
hasLeftSideBearingArray = False
for i in range(numberOfHMetrics, len(glyphOrder)):
glyphName = glyphOrder[i]
lsb = self.metrics[glyphName][1]
if lsb != getattr(glyf[glyphName], "xMin", 0):
hasLeftSideBearingArray = True
break
# if we need to encode both sidebearings arrays, then no transformation is
# applicable, and we must use the untransformed hmtx data
if hasLsbArray and hasLeftSideBearingArray:
return
# set bit 0 and 1 when the respective arrays are _not_ present
flags = 0
if not hasLsbArray:
flags |= 1 << 0
if not hasLeftSideBearingArray:
flags |= 1 << 1
data = struct.pack(">B", flags)
advanceWidthArray = array.array(
"H",
[
self.metrics[glyphName][0]
for i, glyphName in enumerate(glyphOrder)
if i < numberOfHMetrics
]
)
if sys.byteorder != "big":
advanceWidthArray.byteswap()
data += advanceWidthArray.tostring()
if hasLsbArray:
lsbArray = array.array(
"h",
[
self.metrics[glyphName][1]
for i, glyphName in enumerate(glyphOrder)
if i < numberOfHMetrics
]
)
if sys.byteorder != "big":
lsbArray.byteswap()
data += lsbArray.tostring()
if hasLeftSideBearingArray:
leftSideBearingArray = array.array(
"h",
[
self.metrics[glyphOrder[i]][1]
for i in range(numberOfHMetrics, len(glyphOrder))
]
)
if sys.byteorder != "big":
leftSideBearingArray.byteswap()
data += leftSideBearingArray.tostring()
return data
class WOFF2FlavorData(WOFFFlavorData): class WOFF2FlavorData(WOFFFlavorData):
Flavor = 'woff2' Flavor = 'woff2'
def __init__(self, reader=None): def __init__(self, reader=None, transformedTables=None):
"""Data class that holds the WOFF2 header major/minor version, any
metadata or private data (as bytes strings), and the set of
table tags that have transformations applied (if reader is not None),
or will have once the WOFF2 font is compiled.
"""
if not haveBrotli: if not haveBrotli:
raise ImportError("No module named brotli") raise ImportError("No module named brotli")
if reader is not None and transformedTables is not None:
raise TypeError(
"'reader' and 'transformedTables' arguments are mutually exclusive"
)
if transformedTables is None:
transformedTables = woff2TransformedTableTags
else:
if (
"glyf" in transformedTables and "loca" not in transformedTables
or "loca" in transformedTables and "glyf" not in transformedTables
):
raise ValueError(
"'glyf' and 'loca' must be transformed (or not) together"
)
self.majorVersion = None self.majorVersion = None
self.minorVersion = None self.minorVersion = None
self.metaData = None self.metaData = None
@ -935,6 +1172,13 @@ class WOFF2FlavorData(WOFFFlavorData):
data = reader.file.read(reader.privLength) data = reader.file.read(reader.privLength)
assert len(data) == reader.privLength assert len(data) == reader.privLength
self.privData = data self.privData = data
transformedTables = [
tag
for tag, entry in reader.tables.items()
if entry.transformed
]
self.transformedTables = set(transformedTables)
def unpackBase128(data): def unpackBase128(data):
@ -1091,6 +1335,164 @@ def pack255UShort(value):
return struct.pack(">BH", 253, value) return struct.pack(">BH", 253, value)
def compress(input_file, output_file, transform_tables=None):
"""Compress OpenType font to WOFF2.
Args:
input_file: a file path, file or file-like object (open in binary mode)
containing an OpenType font (either CFF- or TrueType-flavored).
output_file: a file path, file or file-like object where to save the
compressed WOFF2 font.
transform_tables: Optional[Iterable[str]]: a set of table tags for which
to enable preprocessing transformations. By default, only 'glyf'
and 'loca' tables are transformed. An empty set means disable all
transformations.
"""
log.info("Processing %s => %s" % (input_file, output_file))
font = TTFont(input_file, recalcBBoxes=False, recalcTimestamp=False)
font.flavor = "woff2"
if transform_tables is not None:
font.flavorData = WOFF2FlavorData(transformedTables=transform_tables)
font.save(output_file, reorderTables=False)
def decompress(input_file, output_file):
"""Decompress WOFF2 font to OpenType font.
Args:
input_file: a file path, file or file-like object (open in binary mode)
containing a compressed WOFF2 font.
output_file: a file path, file or file-like object where to save the
decompressed OpenType font.
"""
log.info("Processing %s => %s" % (input_file, output_file))
font = TTFont(input_file, recalcBBoxes=False, recalcTimestamp=False)
font.flavor = None
font.flavorData = None
font.save(output_file, reorderTables=True)
def main(args=None):
import argparse
from fontTools import configLogger
from fontTools.ttx import makeOutputFileName
class _NoGlyfTransformAction(argparse.Action):
def __call__(self, parser, namespace, values, option_string=None):
namespace.transform_tables.difference_update({"glyf", "loca"})
class _HmtxTransformAction(argparse.Action):
def __call__(self, parser, namespace, values, option_string=None):
namespace.transform_tables.add("hmtx")
parser = argparse.ArgumentParser(
prog="fonttools ttLib.woff2",
description="Compress and decompress WOFF2 fonts",
)
parser_group = parser.add_subparsers(title="sub-commands")
parser_compress = parser_group.add_parser("compress")
parser_decompress = parser_group.add_parser("decompress")
for subparser in (parser_compress, parser_decompress):
group = subparser.add_mutually_exclusive_group(required=False)
group.add_argument(
"-v",
"--verbose",
action="store_true",
help="print more messages to console",
)
group.add_argument(
"-q",
"--quiet",
action="store_true",
help="do not print messages to console",
)
parser_compress.add_argument(
"input_file",
metavar="INPUT",
help="the input OpenType font (.ttf or .otf)",
)
parser_decompress.add_argument(
"input_file",
metavar="INPUT",
help="the input WOFF2 font",
)
parser_compress.add_argument(
"-o",
"--output-file",
metavar="OUTPUT",
help="the output WOFF2 font",
)
parser_decompress.add_argument(
"-o",
"--output-file",
metavar="OUTPUT",
help="the output OpenType font",
)
transform_group = parser_compress.add_argument_group()
transform_group.add_argument(
"--no-glyf-transform",
dest="transform_tables",
nargs=0,
action=_NoGlyfTransformAction,
help="Do not transform glyf (and loca) tables",
)
transform_group.add_argument(
"--hmtx-transform",
dest="transform_tables",
nargs=0,
action=_HmtxTransformAction,
help="Enable optional transformation for 'hmtx' table",
)
parser_compress.set_defaults(
subcommand=compress,
transform_tables={"glyf", "loca"},
)
parser_decompress.set_defaults(subcommand=decompress)
options = vars(parser.parse_args(args))
subcommand = options.pop("subcommand", None)
if not subcommand:
parser.print_help()
return
quiet = options.pop("quiet")
verbose = options.pop("verbose")
configLogger(
level=("ERROR" if quiet else "DEBUG" if verbose else "INFO"),
)
if not options["output_file"]:
if subcommand is compress:
extension = ".woff2"
elif subcommand is decompress:
# choose .ttf/.otf file extension depending on sfntVersion
with open(options["input_file"], "rb") as f:
f.seek(4) # skip 'wOF2' signature
sfntVersion = f.read(4)
assert len(sfntVersion) == 4, "not enough data"
extension = ".otf" if sfntVersion == b"OTTO" else ".ttf"
else:
raise AssertionError(subcommand)
options["output_file"] = makeOutputFileName(
options["input_file"], outputDir=None, extension=extension
)
try:
subcommand(**options)
except TTLibError as e:
parser.error(e)
if __name__ == "__main__": if __name__ == "__main__":
import doctest sys.exit(main())
sys.exit(doctest.testmod().failed)

View File

@ -4,9 +4,9 @@
# Source: https://unicode.org/Public/UNIDATA/Blocks.txt # Source: https://unicode.org/Public/UNIDATA/Blocks.txt
# License: http://unicode.org/copyright.html#License # License: http://unicode.org/copyright.html#License
# #
# Blocks-11.0.0.txt # Blocks-12.1.0.txt
# Date: 2017-10-16, 24:39:00 GMT [KW] # Date: 2019-03-08, 23:59:00 GMT [KW]
# © 2017 Unicode®, Inc. # © 2019 Unicode®, Inc.
# For terms of use, see http://www.unicode.org/terms_of_use.html # For terms of use, see http://www.unicode.org/terms_of_use.html
# #
# Unicode Character Database # Unicode Character Database
@ -237,7 +237,8 @@ RANGES = [
0x10E80, # .. 0x10EFF ; No_Block 0x10E80, # .. 0x10EFF ; No_Block
0x10F00, # .. 0x10F2F ; Old Sogdian 0x10F00, # .. 0x10F2F ; Old Sogdian
0x10F30, # .. 0x10F6F ; Sogdian 0x10F30, # .. 0x10F6F ; Sogdian
0x10F70, # .. 0x10FFF ; No_Block 0x10F70, # .. 0x10FDF ; No_Block
0x10FE0, # .. 0x10FFF ; Elymaic
0x11000, # .. 0x1107F ; Brahmi 0x11000, # .. 0x1107F ; Brahmi
0x11080, # .. 0x110CF ; Kaithi 0x11080, # .. 0x110CF ; Kaithi
0x110D0, # .. 0x110FF ; Sora Sompeng 0x110D0, # .. 0x110FF ; Sora Sompeng
@ -264,7 +265,8 @@ RANGES = [
0x11800, # .. 0x1184F ; Dogra 0x11800, # .. 0x1184F ; Dogra
0x11850, # .. 0x1189F ; No_Block 0x11850, # .. 0x1189F ; No_Block
0x118A0, # .. 0x118FF ; Warang Citi 0x118A0, # .. 0x118FF ; Warang Citi
0x11900, # .. 0x119FF ; No_Block 0x11900, # .. 0x1199F ; No_Block
0x119A0, # .. 0x119FF ; Nandinagari
0x11A00, # .. 0x11A4F ; Zanabazar Square 0x11A00, # .. 0x11A4F ; Zanabazar Square
0x11A50, # .. 0x11AAF ; Soyombo 0x11A50, # .. 0x11AAF ; Soyombo
0x11AB0, # .. 0x11ABF ; No_Block 0x11AB0, # .. 0x11ABF ; No_Block
@ -277,13 +279,15 @@ RANGES = [
0x11D60, # .. 0x11DAF ; Gunjala Gondi 0x11D60, # .. 0x11DAF ; Gunjala Gondi
0x11DB0, # .. 0x11EDF ; No_Block 0x11DB0, # .. 0x11EDF ; No_Block
0x11EE0, # .. 0x11EFF ; Makasar 0x11EE0, # .. 0x11EFF ; Makasar
0x11F00, # .. 0x11FFF ; No_Block 0x11F00, # .. 0x11FBF ; No_Block
0x11FC0, # .. 0x11FFF ; Tamil Supplement
0x12000, # .. 0x123FF ; Cuneiform 0x12000, # .. 0x123FF ; Cuneiform
0x12400, # .. 0x1247F ; Cuneiform Numbers and Punctuation 0x12400, # .. 0x1247F ; Cuneiform Numbers and Punctuation
0x12480, # .. 0x1254F ; Early Dynastic Cuneiform 0x12480, # .. 0x1254F ; Early Dynastic Cuneiform
0x12550, # .. 0x12FFF ; No_Block 0x12550, # .. 0x12FFF ; No_Block
0x13000, # .. 0x1342F ; Egyptian Hieroglyphs 0x13000, # .. 0x1342F ; Egyptian Hieroglyphs
0x13430, # .. 0x143FF ; No_Block 0x13430, # .. 0x1343F ; Egyptian Hieroglyph Format Controls
0x13440, # .. 0x143FF ; No_Block
0x14400, # .. 0x1467F ; Anatolian Hieroglyphs 0x14400, # .. 0x1467F ; Anatolian Hieroglyphs
0x14680, # .. 0x167FF ; No_Block 0x14680, # .. 0x167FF ; No_Block
0x16800, # .. 0x16A3F ; Bamum Supplement 0x16800, # .. 0x16A3F ; Bamum Supplement
@ -302,7 +306,7 @@ RANGES = [
0x18B00, # .. 0x1AFFF ; No_Block 0x18B00, # .. 0x1AFFF ; No_Block
0x1B000, # .. 0x1B0FF ; Kana Supplement 0x1B000, # .. 0x1B0FF ; Kana Supplement
0x1B100, # .. 0x1B12F ; Kana Extended-A 0x1B100, # .. 0x1B12F ; Kana Extended-A
0x1B130, # .. 0x1B16F ; No_Block 0x1B130, # .. 0x1B16F ; Small Kana Extension
0x1B170, # .. 0x1B2FF ; Nushu 0x1B170, # .. 0x1B2FF ; Nushu
0x1B300, # .. 0x1BBFF ; No_Block 0x1B300, # .. 0x1BBFF ; No_Block
0x1BC00, # .. 0x1BC9F ; Duployan 0x1BC00, # .. 0x1BC9F ; Duployan
@ -320,13 +324,19 @@ RANGES = [
0x1D800, # .. 0x1DAAF ; Sutton SignWriting 0x1D800, # .. 0x1DAAF ; Sutton SignWriting
0x1DAB0, # .. 0x1DFFF ; No_Block 0x1DAB0, # .. 0x1DFFF ; No_Block
0x1E000, # .. 0x1E02F ; Glagolitic Supplement 0x1E000, # .. 0x1E02F ; Glagolitic Supplement
0x1E030, # .. 0x1E7FF ; No_Block 0x1E030, # .. 0x1E0FF ; No_Block
0x1E100, # .. 0x1E14F ; Nyiakeng Puachue Hmong
0x1E150, # .. 0x1E2BF ; No_Block
0x1E2C0, # .. 0x1E2FF ; Wancho
0x1E300, # .. 0x1E7FF ; No_Block
0x1E800, # .. 0x1E8DF ; Mende Kikakui 0x1E800, # .. 0x1E8DF ; Mende Kikakui
0x1E8E0, # .. 0x1E8FF ; No_Block 0x1E8E0, # .. 0x1E8FF ; No_Block
0x1E900, # .. 0x1E95F ; Adlam 0x1E900, # .. 0x1E95F ; Adlam
0x1E960, # .. 0x1EC6F ; No_Block 0x1E960, # .. 0x1EC6F ; No_Block
0x1EC70, # .. 0x1ECBF ; Indic Siyaq Numbers 0x1EC70, # .. 0x1ECBF ; Indic Siyaq Numbers
0x1ECC0, # .. 0x1EDFF ; No_Block 0x1ECC0, # .. 0x1ECFF ; No_Block
0x1ED00, # .. 0x1ED4F ; Ottoman Siyaq Numbers
0x1ED50, # .. 0x1EDFF ; No_Block
0x1EE00, # .. 0x1EEFF ; Arabic Mathematical Alphabetic Symbols 0x1EE00, # .. 0x1EEFF ; Arabic Mathematical Alphabetic Symbols
0x1EF00, # .. 0x1EFFF ; No_Block 0x1EF00, # .. 0x1EFFF ; No_Block
0x1F000, # .. 0x1F02F ; Mahjong Tiles 0x1F000, # .. 0x1F02F ; Mahjong Tiles
@ -343,7 +353,8 @@ RANGES = [
0x1F800, # .. 0x1F8FF ; Supplemental Arrows-C 0x1F800, # .. 0x1F8FF ; Supplemental Arrows-C
0x1F900, # .. 0x1F9FF ; Supplemental Symbols and Pictographs 0x1F900, # .. 0x1F9FF ; Supplemental Symbols and Pictographs
0x1FA00, # .. 0x1FA6F ; Chess Symbols 0x1FA00, # .. 0x1FA6F ; Chess Symbols
0x1FA70, # .. 0x1FFFF ; No_Block 0x1FA70, # .. 0x1FAFF ; Symbols and Pictographs Extended-A
0x1FB00, # .. 0x1FFFF ; No_Block
0x20000, # .. 0x2A6DF ; CJK Unified Ideographs Extension B 0x20000, # .. 0x2A6DF ; CJK Unified Ideographs Extension B
0x2A6E0, # .. 0x2A6FF ; No_Block 0x2A6E0, # .. 0x2A6FF ; No_Block
0x2A700, # .. 0x2B73F ; CJK Unified Ideographs Extension C 0x2A700, # .. 0x2B73F ; CJK Unified Ideographs Extension C
@ -582,7 +593,8 @@ VALUES = [
'No_Block', # 10E80..10EFF 'No_Block', # 10E80..10EFF
'Old Sogdian', # 10F00..10F2F 'Old Sogdian', # 10F00..10F2F
'Sogdian', # 10F30..10F6F 'Sogdian', # 10F30..10F6F
'No_Block', # 10F70..10FFF 'No_Block', # 10F70..10FDF
'Elymaic', # 10FE0..10FFF
'Brahmi', # 11000..1107F 'Brahmi', # 11000..1107F
'Kaithi', # 11080..110CF 'Kaithi', # 11080..110CF
'Sora Sompeng', # 110D0..110FF 'Sora Sompeng', # 110D0..110FF
@ -609,7 +621,8 @@ VALUES = [
'Dogra', # 11800..1184F 'Dogra', # 11800..1184F
'No_Block', # 11850..1189F 'No_Block', # 11850..1189F
'Warang Citi', # 118A0..118FF 'Warang Citi', # 118A0..118FF
'No_Block', # 11900..119FF 'No_Block', # 11900..1199F
'Nandinagari', # 119A0..119FF
'Zanabazar Square', # 11A00..11A4F 'Zanabazar Square', # 11A00..11A4F
'Soyombo', # 11A50..11AAF 'Soyombo', # 11A50..11AAF
'No_Block', # 11AB0..11ABF 'No_Block', # 11AB0..11ABF
@ -622,13 +635,15 @@ VALUES = [
'Gunjala Gondi', # 11D60..11DAF 'Gunjala Gondi', # 11D60..11DAF
'No_Block', # 11DB0..11EDF 'No_Block', # 11DB0..11EDF
'Makasar', # 11EE0..11EFF 'Makasar', # 11EE0..11EFF
'No_Block', # 11F00..11FFF 'No_Block', # 11F00..11FBF
'Tamil Supplement', # 11FC0..11FFF
'Cuneiform', # 12000..123FF 'Cuneiform', # 12000..123FF
'Cuneiform Numbers and Punctuation', # 12400..1247F 'Cuneiform Numbers and Punctuation', # 12400..1247F
'Early Dynastic Cuneiform', # 12480..1254F 'Early Dynastic Cuneiform', # 12480..1254F
'No_Block', # 12550..12FFF 'No_Block', # 12550..12FFF
'Egyptian Hieroglyphs', # 13000..1342F 'Egyptian Hieroglyphs', # 13000..1342F
'No_Block', # 13430..143FF 'Egyptian Hieroglyph Format Controls', # 13430..1343F
'No_Block', # 13440..143FF
'Anatolian Hieroglyphs', # 14400..1467F 'Anatolian Hieroglyphs', # 14400..1467F
'No_Block', # 14680..167FF 'No_Block', # 14680..167FF
'Bamum Supplement', # 16800..16A3F 'Bamum Supplement', # 16800..16A3F
@ -647,7 +662,7 @@ VALUES = [
'No_Block', # 18B00..1AFFF 'No_Block', # 18B00..1AFFF
'Kana Supplement', # 1B000..1B0FF 'Kana Supplement', # 1B000..1B0FF
'Kana Extended-A', # 1B100..1B12F 'Kana Extended-A', # 1B100..1B12F
'No_Block', # 1B130..1B16F 'Small Kana Extension', # 1B130..1B16F
'Nushu', # 1B170..1B2FF 'Nushu', # 1B170..1B2FF
'No_Block', # 1B300..1BBFF 'No_Block', # 1B300..1BBFF
'Duployan', # 1BC00..1BC9F 'Duployan', # 1BC00..1BC9F
@ -665,13 +680,19 @@ VALUES = [
'Sutton SignWriting', # 1D800..1DAAF 'Sutton SignWriting', # 1D800..1DAAF
'No_Block', # 1DAB0..1DFFF 'No_Block', # 1DAB0..1DFFF
'Glagolitic Supplement', # 1E000..1E02F 'Glagolitic Supplement', # 1E000..1E02F
'No_Block', # 1E030..1E7FF 'No_Block', # 1E030..1E0FF
'Nyiakeng Puachue Hmong', # 1E100..1E14F
'No_Block', # 1E150..1E2BF
'Wancho', # 1E2C0..1E2FF
'No_Block', # 1E300..1E7FF
'Mende Kikakui', # 1E800..1E8DF 'Mende Kikakui', # 1E800..1E8DF
'No_Block', # 1E8E0..1E8FF 'No_Block', # 1E8E0..1E8FF
'Adlam', # 1E900..1E95F 'Adlam', # 1E900..1E95F
'No_Block', # 1E960..1EC6F 'No_Block', # 1E960..1EC6F
'Indic Siyaq Numbers', # 1EC70..1ECBF 'Indic Siyaq Numbers', # 1EC70..1ECBF
'No_Block', # 1ECC0..1EDFF 'No_Block', # 1ECC0..1ECFF
'Ottoman Siyaq Numbers', # 1ED00..1ED4F
'No_Block', # 1ED50..1EDFF
'Arabic Mathematical Alphabetic Symbols', # 1EE00..1EEFF 'Arabic Mathematical Alphabetic Symbols', # 1EE00..1EEFF
'No_Block', # 1EF00..1EFFF 'No_Block', # 1EF00..1EFFF
'Mahjong Tiles', # 1F000..1F02F 'Mahjong Tiles', # 1F000..1F02F
@ -688,7 +709,8 @@ VALUES = [
'Supplemental Arrows-C', # 1F800..1F8FF 'Supplemental Arrows-C', # 1F800..1F8FF
'Supplemental Symbols and Pictographs', # 1F900..1F9FF 'Supplemental Symbols and Pictographs', # 1F900..1F9FF
'Chess Symbols', # 1FA00..1FA6F 'Chess Symbols', # 1FA00..1FA6F
'No_Block', # 1FA70..1FFFF 'Symbols and Pictographs Extended-A', # 1FA70..1FAFF
'No_Block', # 1FB00..1FFFF
'CJK Unified Ideographs Extension B', # 20000..2A6DF 'CJK Unified Ideographs Extension B', # 20000..2A6DF
'No_Block', # 2A6E0..2A6FF 'No_Block', # 2A6E0..2A6FF
'CJK Unified Ideographs Extension C', # 2A700..2B73F 'CJK Unified Ideographs Extension C', # 2A700..2B73F

View File

@ -4,9 +4,9 @@
# Source: https://unicode.org/Public/UNIDATA/ScriptExtensions.txt # Source: https://unicode.org/Public/UNIDATA/ScriptExtensions.txt
# License: http://unicode.org/copyright.html#License # License: http://unicode.org/copyright.html#License
# #
# ScriptExtensions-11.0.0.txt # ScriptExtensions-12.1.0.txt
# Date: 2018-02-04, 20:04:00 GMT # Date: 2019-04-01, 09:10:42 GMT
# © 2018 Unicode®, Inc. # © 2019 Unicode®, Inc.
# Unicode and the Unicode Logo are registered trademarks of Unicode, Inc. in the U.S. and other countries. # Unicode and the Unicode Logo are registered trademarks of Unicode, Inc. in the U.S. and other countries.
# For terms of use, see http://www.unicode.org/terms_of_use.html # For terms of use, see http://www.unicode.org/terms_of_use.html
# #
@ -75,8 +75,8 @@ RANGES = [
0x0951, # .. 0x0951 ; {'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Shrd', 'Taml', 'Telu', 'Tirh'} 0x0951, # .. 0x0951 ; {'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Shrd', 'Taml', 'Telu', 'Tirh'}
0x0952, # .. 0x0952 ; {'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Taml', 'Telu', 'Tirh'} 0x0952, # .. 0x0952 ; {'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Taml', 'Telu', 'Tirh'}
0x0953, # .. 0x0963 ; None 0x0953, # .. 0x0963 ; None
0x0964, # .. 0x0964 ; {'Beng', 'Deva', 'Dogr', 'Gong', 'Gran', 'Gujr', 'Guru', 'Knda', 'Mahj', 'Mlym', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'} 0x0964, # .. 0x0964 ; {'Beng', 'Deva', 'Dogr', 'Gong', 'Gonm', 'Gran', 'Gujr', 'Guru', 'Knda', 'Mahj', 'Mlym', 'Nand', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'}
0x0965, # .. 0x0965 ; {'Beng', 'Deva', 'Dogr', 'Gong', 'Gran', 'Gujr', 'Guru', 'Knda', 'Limb', 'Mahj', 'Mlym', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'} 0x0965, # .. 0x0965 ; {'Beng', 'Deva', 'Dogr', 'Gong', 'Gonm', 'Gran', 'Gujr', 'Guru', 'Knda', 'Limb', 'Mahj', 'Mlym', 'Nand', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'}
0x0966, # .. 0x096F ; {'Deva', 'Dogr', 'Kthi', 'Mahj'} 0x0966, # .. 0x096F ; {'Deva', 'Dogr', 'Kthi', 'Mahj'}
0x0970, # .. 0x09E5 ; None 0x0970, # .. 0x09E5 ; None
0x09E6, # .. 0x09EF ; {'Beng', 'Cakm', 'Sylo'} 0x09E6, # .. 0x09EF ; {'Beng', 'Cakm', 'Sylo'}
@ -86,7 +86,9 @@ RANGES = [
0x0AE6, # .. 0x0AEF ; {'Gujr', 'Khoj'} 0x0AE6, # .. 0x0AEF ; {'Gujr', 'Khoj'}
0x0AF0, # .. 0x0BE5 ; None 0x0AF0, # .. 0x0BE5 ; None
0x0BE6, # .. 0x0BF3 ; {'Gran', 'Taml'} 0x0BE6, # .. 0x0BF3 ; {'Gran', 'Taml'}
0x0BF4, # .. 0x103F ; None 0x0BF4, # .. 0x0CE5 ; None
0x0CE6, # .. 0x0CEF ; {'Knda', 'Nand'}
0x0CF0, # .. 0x103F ; None
0x1040, # .. 0x1049 ; {'Cakm', 'Mymr', 'Tale'} 0x1040, # .. 0x1049 ; {'Cakm', 'Mymr', 'Tale'}
0x104A, # .. 0x10FA ; None 0x104A, # .. 0x10FA ; None
0x10FB, # .. 0x10FB ; {'Geor', 'Latn'} 0x10FB, # .. 0x10FB ; {'Geor', 'Latn'}
@ -112,19 +114,24 @@ RANGES = [
0x1CDE, # .. 0x1CDF ; {'Deva'} 0x1CDE, # .. 0x1CDF ; {'Deva'}
0x1CE0, # .. 0x1CE0 ; {'Deva', 'Shrd'} 0x1CE0, # .. 0x1CE0 ; {'Deva', 'Shrd'}
0x1CE1, # .. 0x1CE1 ; {'Beng', 'Deva'} 0x1CE1, # .. 0x1CE1 ; {'Beng', 'Deva'}
0x1CE2, # .. 0x1CE9 ; {'Deva'} 0x1CE2, # .. 0x1CE8 ; {'Deva'}
0x1CE9, # .. 0x1CE9 ; {'Deva', 'Nand'}
0x1CEA, # .. 0x1CEA ; {'Beng', 'Deva'} 0x1CEA, # .. 0x1CEA ; {'Beng', 'Deva'}
0x1CEB, # .. 0x1CEC ; {'Deva'} 0x1CEB, # .. 0x1CEC ; {'Deva'}
0x1CED, # .. 0x1CED ; {'Beng', 'Deva'} 0x1CED, # .. 0x1CED ; {'Beng', 'Deva'}
0x1CEE, # .. 0x1CF1 ; {'Deva'} 0x1CEE, # .. 0x1CF1 ; {'Deva'}
0x1CF2, # .. 0x1CF3 ; {'Deva', 'Gran'} 0x1CF2, # .. 0x1CF2 ; {'Beng', 'Deva', 'Gran', 'Knda', 'Nand', 'Orya', 'Telu', 'Tirh'}
0x1CF3, # .. 0x1CF3 ; {'Deva', 'Gran'}
0x1CF4, # .. 0x1CF4 ; {'Deva', 'Gran', 'Knda'} 0x1CF4, # .. 0x1CF4 ; {'Deva', 'Gran', 'Knda'}
0x1CF5, # .. 0x1CF6 ; {'Beng', 'Deva'} 0x1CF5, # .. 0x1CF6 ; {'Beng', 'Deva'}
0x1CF7, # .. 0x1CF7 ; {'Beng'} 0x1CF7, # .. 0x1CF7 ; {'Beng'}
0x1CF8, # .. 0x1CF9 ; {'Deva', 'Gran'} 0x1CF8, # .. 0x1CF9 ; {'Deva', 'Gran'}
0x1CFA, # .. 0x1DBF ; None 0x1CFA, # .. 0x1CFA ; {'Nand'}
0x1CFB, # .. 0x1DBF ; None
0x1DC0, # .. 0x1DC1 ; {'Grek'} 0x1DC0, # .. 0x1DC1 ; {'Grek'}
0x1DC2, # .. 0x20EF ; None 0x1DC2, # .. 0x202E ; None
0x202F, # .. 0x202F ; {'Latn', 'Mong'}
0x2030, # .. 0x20EF ; None
0x20F0, # .. 0x20F0 ; {'Deva', 'Gran', 'Latn'} 0x20F0, # .. 0x20F0 ; {'Deva', 'Gran', 'Latn'}
0x20F1, # .. 0x2E42 ; None 0x20F1, # .. 0x2E42 ; None
0x2E43, # .. 0x2E43 ; {'Cyrl', 'Glag'} 0x2E43, # .. 0x2E43 ; {'Cyrl', 'Glag'}
@ -166,7 +173,9 @@ RANGES = [
0x3280, # .. 0x32B0 ; {'Hani'} 0x3280, # .. 0x32B0 ; {'Hani'}
0x32B1, # .. 0x32BF ; None 0x32B1, # .. 0x32BF ; None
0x32C0, # .. 0x32CB ; {'Hani'} 0x32C0, # .. 0x32CB ; {'Hani'}
0x32CC, # .. 0x3357 ; None 0x32CC, # .. 0x32FE ; None
0x32FF, # .. 0x32FF ; {'Hani'}
0x3300, # .. 0x3357 ; None
0x3358, # .. 0x3370 ; {'Hani'} 0x3358, # .. 0x3370 ; {'Hani'}
0x3371, # .. 0x337A ; None 0x3371, # .. 0x337A ; None
0x337B, # .. 0x337F ; {'Hani'} 0x337B, # .. 0x337F ; {'Hani'}
@ -175,8 +184,8 @@ RANGES = [
0x33FF, # .. 0xA66E ; None 0x33FF, # .. 0xA66E ; None
0xA66F, # .. 0xA66F ; {'Cyrl', 'Glag'} 0xA66F, # .. 0xA66F ; {'Cyrl', 'Glag'}
0xA670, # .. 0xA82F ; None 0xA670, # .. 0xA82F ; None
0xA830, # .. 0xA832 ; {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Mlym', 'Modi', 'Sind', 'Takr', 'Tirh'} 0xA830, # .. 0xA832 ; {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Mlym', 'Modi', 'Nand', 'Sind', 'Takr', 'Tirh'}
0xA833, # .. 0xA835 ; {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Modi', 'Sind', 'Takr', 'Tirh'} 0xA833, # .. 0xA835 ; {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Modi', 'Nand', 'Sind', 'Takr', 'Tirh'}
0xA836, # .. 0xA839 ; {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Kthi', 'Mahj', 'Modi', 'Sind', 'Takr', 'Tirh'} 0xA836, # .. 0xA839 ; {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Kthi', 'Mahj', 'Modi', 'Sind', 'Takr', 'Tirh'}
0xA83A, # .. 0xA8F0 ; None 0xA83A, # .. 0xA8F0 ; None
0xA8F1, # .. 0xA8F1 ; {'Beng', 'Deva'} 0xA8F1, # .. 0xA8F1 ; {'Beng', 'Deva'}
@ -212,7 +221,11 @@ RANGES = [
0x11303, # .. 0x11303 ; {'Gran', 'Taml'} 0x11303, # .. 0x11303 ; {'Gran', 'Taml'}
0x11304, # .. 0x1133A ; None 0x11304, # .. 0x1133A ; None
0x1133B, # .. 0x1133C ; {'Gran', 'Taml'} 0x1133B, # .. 0x1133C ; {'Gran', 'Taml'}
0x1133D, # .. 0x1BC9F ; None 0x1133D, # .. 0x11FCF ; None
0x11FD0, # .. 0x11FD1 ; {'Gran', 'Taml'}
0x11FD2, # .. 0x11FD2 ; None
0x11FD3, # .. 0x11FD3 ; {'Gran', 'Taml'}
0x11FD4, # .. 0x1BC9F ; None
0x1BCA0, # .. 0x1BCA3 ; {'Dupl'} 0x1BCA0, # .. 0x1BCA3 ; {'Dupl'}
0x1BCA4, # .. 0x1D35F ; None 0x1BCA4, # .. 0x1D35F ; None
0x1D360, # .. 0x1D371 ; {'Hani'} 0x1D360, # .. 0x1D371 ; {'Hani'}
@ -256,8 +269,8 @@ VALUES = [
{'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Shrd', 'Taml', 'Telu', 'Tirh'}, # 0951..0951 {'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Shrd', 'Taml', 'Telu', 'Tirh'}, # 0951..0951
{'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Taml', 'Telu', 'Tirh'}, # 0952..0952 {'Beng', 'Deva', 'Gran', 'Gujr', 'Guru', 'Knda', 'Latn', 'Mlym', 'Orya', 'Taml', 'Telu', 'Tirh'}, # 0952..0952
None, # 0953..0963 None, # 0953..0963
{'Beng', 'Deva', 'Dogr', 'Gong', 'Gran', 'Gujr', 'Guru', 'Knda', 'Mahj', 'Mlym', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'}, # 0964..0964 {'Beng', 'Deva', 'Dogr', 'Gong', 'Gonm', 'Gran', 'Gujr', 'Guru', 'Knda', 'Mahj', 'Mlym', 'Nand', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'}, # 0964..0964
{'Beng', 'Deva', 'Dogr', 'Gong', 'Gran', 'Gujr', 'Guru', 'Knda', 'Limb', 'Mahj', 'Mlym', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'}, # 0965..0965 {'Beng', 'Deva', 'Dogr', 'Gong', 'Gonm', 'Gran', 'Gujr', 'Guru', 'Knda', 'Limb', 'Mahj', 'Mlym', 'Nand', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Telu', 'Tirh'}, # 0965..0965
{'Deva', 'Dogr', 'Kthi', 'Mahj'}, # 0966..096F {'Deva', 'Dogr', 'Kthi', 'Mahj'}, # 0966..096F
None, # 0970..09E5 None, # 0970..09E5
{'Beng', 'Cakm', 'Sylo'}, # 09E6..09EF {'Beng', 'Cakm', 'Sylo'}, # 09E6..09EF
@ -267,7 +280,9 @@ VALUES = [
{'Gujr', 'Khoj'}, # 0AE6..0AEF {'Gujr', 'Khoj'}, # 0AE6..0AEF
None, # 0AF0..0BE5 None, # 0AF0..0BE5
{'Gran', 'Taml'}, # 0BE6..0BF3 {'Gran', 'Taml'}, # 0BE6..0BF3
None, # 0BF4..103F None, # 0BF4..0CE5
{'Knda', 'Nand'}, # 0CE6..0CEF
None, # 0CF0..103F
{'Cakm', 'Mymr', 'Tale'}, # 1040..1049 {'Cakm', 'Mymr', 'Tale'}, # 1040..1049
None, # 104A..10FA None, # 104A..10FA
{'Geor', 'Latn'}, # 10FB..10FB {'Geor', 'Latn'}, # 10FB..10FB
@ -293,19 +308,24 @@ VALUES = [
{'Deva'}, # 1CDE..1CDF {'Deva'}, # 1CDE..1CDF
{'Deva', 'Shrd'}, # 1CE0..1CE0 {'Deva', 'Shrd'}, # 1CE0..1CE0
{'Beng', 'Deva'}, # 1CE1..1CE1 {'Beng', 'Deva'}, # 1CE1..1CE1
{'Deva'}, # 1CE2..1CE9 {'Deva'}, # 1CE2..1CE8
{'Deva', 'Nand'}, # 1CE9..1CE9
{'Beng', 'Deva'}, # 1CEA..1CEA {'Beng', 'Deva'}, # 1CEA..1CEA
{'Deva'}, # 1CEB..1CEC {'Deva'}, # 1CEB..1CEC
{'Beng', 'Deva'}, # 1CED..1CED {'Beng', 'Deva'}, # 1CED..1CED
{'Deva'}, # 1CEE..1CF1 {'Deva'}, # 1CEE..1CF1
{'Deva', 'Gran'}, # 1CF2..1CF3 {'Beng', 'Deva', 'Gran', 'Knda', 'Nand', 'Orya', 'Telu', 'Tirh'}, # 1CF2..1CF2
{'Deva', 'Gran'}, # 1CF3..1CF3
{'Deva', 'Gran', 'Knda'}, # 1CF4..1CF4 {'Deva', 'Gran', 'Knda'}, # 1CF4..1CF4
{'Beng', 'Deva'}, # 1CF5..1CF6 {'Beng', 'Deva'}, # 1CF5..1CF6
{'Beng'}, # 1CF7..1CF7 {'Beng'}, # 1CF7..1CF7
{'Deva', 'Gran'}, # 1CF8..1CF9 {'Deva', 'Gran'}, # 1CF8..1CF9
None, # 1CFA..1DBF {'Nand'}, # 1CFA..1CFA
None, # 1CFB..1DBF
{'Grek'}, # 1DC0..1DC1 {'Grek'}, # 1DC0..1DC1
None, # 1DC2..20EF None, # 1DC2..202E
{'Latn', 'Mong'}, # 202F..202F
None, # 2030..20EF
{'Deva', 'Gran', 'Latn'}, # 20F0..20F0 {'Deva', 'Gran', 'Latn'}, # 20F0..20F0
None, # 20F1..2E42 None, # 20F1..2E42
{'Cyrl', 'Glag'}, # 2E43..2E43 {'Cyrl', 'Glag'}, # 2E43..2E43
@ -347,7 +367,9 @@ VALUES = [
{'Hani'}, # 3280..32B0 {'Hani'}, # 3280..32B0
None, # 32B1..32BF None, # 32B1..32BF
{'Hani'}, # 32C0..32CB {'Hani'}, # 32C0..32CB
None, # 32CC..3357 None, # 32CC..32FE
{'Hani'}, # 32FF..32FF
None, # 3300..3357
{'Hani'}, # 3358..3370 {'Hani'}, # 3358..3370
None, # 3371..337A None, # 3371..337A
{'Hani'}, # 337B..337F {'Hani'}, # 337B..337F
@ -356,8 +378,8 @@ VALUES = [
None, # 33FF..A66E None, # 33FF..A66E
{'Cyrl', 'Glag'}, # A66F..A66F {'Cyrl', 'Glag'}, # A66F..A66F
None, # A670..A82F None, # A670..A82F
{'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Mlym', 'Modi', 'Sind', 'Takr', 'Tirh'}, # A830..A832 {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Mlym', 'Modi', 'Nand', 'Sind', 'Takr', 'Tirh'}, # A830..A832
{'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Modi', 'Sind', 'Takr', 'Tirh'}, # A833..A835 {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Knda', 'Kthi', 'Mahj', 'Modi', 'Nand', 'Sind', 'Takr', 'Tirh'}, # A833..A835
{'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Kthi', 'Mahj', 'Modi', 'Sind', 'Takr', 'Tirh'}, # A836..A839 {'Deva', 'Dogr', 'Gujr', 'Guru', 'Khoj', 'Kthi', 'Mahj', 'Modi', 'Sind', 'Takr', 'Tirh'}, # A836..A839
None, # A83A..A8F0 None, # A83A..A8F0
{'Beng', 'Deva'}, # A8F1..A8F1 {'Beng', 'Deva'}, # A8F1..A8F1
@ -393,7 +415,11 @@ VALUES = [
{'Gran', 'Taml'}, # 11303..11303 {'Gran', 'Taml'}, # 11303..11303
None, # 11304..1133A None, # 11304..1133A
{'Gran', 'Taml'}, # 1133B..1133C {'Gran', 'Taml'}, # 1133B..1133C
None, # 1133D..1BC9F None, # 1133D..11FCF
{'Gran', 'Taml'}, # 11FD0..11FD1
None, # 11FD2..11FD2
{'Gran', 'Taml'}, # 11FD3..11FD3
None, # 11FD4..1BC9F
{'Dupl'}, # 1BCA0..1BCA3 {'Dupl'}, # 1BCA0..1BCA3
None, # 1BCA4..1D35F None, # 1BCA4..1D35F
{'Hani'}, # 1D360..1D371 {'Hani'}, # 1D360..1D371

View File

@ -4,9 +4,9 @@
# Source: https://unicode.org/Public/UNIDATA/Scripts.txt # Source: https://unicode.org/Public/UNIDATA/Scripts.txt
# License: http://unicode.org/copyright.html#License # License: http://unicode.org/copyright.html#License
# #
# Scripts-11.0.0.txt # Scripts-12.1.0.txt
# Date: 2018-02-21, 05:34:31 GMT # Date: 2019-04-01, 09:10:42 GMT
# © 2018 Unicode®, Inc. # © 2019 Unicode®, Inc.
# Unicode and the Unicode Logo are registered trademarks of Unicode, Inc. in the U.S. and other countries. # Unicode and the Unicode Logo are registered trademarks of Unicode, Inc. in the U.S. and other countries.
# For terms of use, see http://www.unicode.org/terms_of_use.html # For terms of use, see http://www.unicode.org/terms_of_use.html
# #
@ -128,8 +128,8 @@ RANGES = [
0x08E2, # .. 0x08E2 ; Common 0x08E2, # .. 0x08E2 ; Common
0x08E3, # .. 0x08FF ; Arabic 0x08E3, # .. 0x08FF ; Arabic
0x0900, # .. 0x0950 ; Devanagari 0x0900, # .. 0x0950 ; Devanagari
0x0951, # .. 0x0952 ; Inherited 0x0951, # .. 0x0954 ; Inherited
0x0953, # .. 0x0963 ; Devanagari 0x0955, # .. 0x0963 ; Devanagari
0x0964, # .. 0x0965 ; Common 0x0964, # .. 0x0965 ; Common
0x0966, # .. 0x097F ; Devanagari 0x0966, # .. 0x097F ; Devanagari
0x0980, # .. 0x0983 ; Bengali 0x0980, # .. 0x0983 ; Bengali
@ -301,8 +301,8 @@ RANGES = [
0x0C60, # .. 0x0C63 ; Telugu 0x0C60, # .. 0x0C63 ; Telugu
0x0C64, # .. 0x0C65 ; Unknown 0x0C64, # .. 0x0C65 ; Unknown
0x0C66, # .. 0x0C6F ; Telugu 0x0C66, # .. 0x0C6F ; Telugu
0x0C70, # .. 0x0C77 ; Unknown 0x0C70, # .. 0x0C76 ; Unknown
0x0C78, # .. 0x0C7F ; Telugu 0x0C77, # .. 0x0C7F ; Telugu
0x0C80, # .. 0x0C8C ; Kannada 0x0C80, # .. 0x0C8C ; Kannada
0x0C8D, # .. 0x0C8D ; Unknown 0x0C8D, # .. 0x0C8D ; Unknown
0x0C8E, # .. 0x0C90 ; Kannada 0x0C8E, # .. 0x0C90 ; Kannada
@ -377,28 +377,14 @@ RANGES = [
0x0E81, # .. 0x0E82 ; Lao 0x0E81, # .. 0x0E82 ; Lao
0x0E83, # .. 0x0E83 ; Unknown 0x0E83, # .. 0x0E83 ; Unknown
0x0E84, # .. 0x0E84 ; Lao 0x0E84, # .. 0x0E84 ; Lao
0x0E85, # .. 0x0E86 ; Unknown 0x0E85, # .. 0x0E85 ; Unknown
0x0E87, # .. 0x0E88 ; Lao 0x0E86, # .. 0x0E8A ; Lao
0x0E89, # .. 0x0E89 ; Unknown 0x0E8B, # .. 0x0E8B ; Unknown
0x0E8A, # .. 0x0E8A ; Lao 0x0E8C, # .. 0x0EA3 ; Lao
0x0E8B, # .. 0x0E8C ; Unknown
0x0E8D, # .. 0x0E8D ; Lao
0x0E8E, # .. 0x0E93 ; Unknown
0x0E94, # .. 0x0E97 ; Lao
0x0E98, # .. 0x0E98 ; Unknown
0x0E99, # .. 0x0E9F ; Lao
0x0EA0, # .. 0x0EA0 ; Unknown
0x0EA1, # .. 0x0EA3 ; Lao
0x0EA4, # .. 0x0EA4 ; Unknown 0x0EA4, # .. 0x0EA4 ; Unknown
0x0EA5, # .. 0x0EA5 ; Lao 0x0EA5, # .. 0x0EA5 ; Lao
0x0EA6, # .. 0x0EA6 ; Unknown 0x0EA6, # .. 0x0EA6 ; Unknown
0x0EA7, # .. 0x0EA7 ; Lao 0x0EA7, # .. 0x0EBD ; Lao
0x0EA8, # .. 0x0EA9 ; Unknown
0x0EAA, # .. 0x0EAB ; Lao
0x0EAC, # .. 0x0EAC ; Unknown
0x0EAD, # .. 0x0EB9 ; Lao
0x0EBA, # .. 0x0EBA ; Unknown
0x0EBB, # .. 0x0EBD ; Lao
0x0EBE, # .. 0x0EBF ; Unknown 0x0EBE, # .. 0x0EBF ; Unknown
0x0EC0, # .. 0x0EC4 ; Lao 0x0EC0, # .. 0x0EC4 ; Lao
0x0EC5, # .. 0x0EC5 ; Unknown 0x0EC5, # .. 0x0EC5 ; Unknown
@ -585,7 +571,8 @@ RANGES = [
0x1CF4, # .. 0x1CF4 ; Inherited 0x1CF4, # .. 0x1CF4 ; Inherited
0x1CF5, # .. 0x1CF7 ; Common 0x1CF5, # .. 0x1CF7 ; Common
0x1CF8, # .. 0x1CF9 ; Inherited 0x1CF8, # .. 0x1CF9 ; Inherited
0x1CFA, # .. 0x1CFF ; Unknown 0x1CFA, # .. 0x1CFA ; Common
0x1CFB, # .. 0x1CFF ; Unknown
0x1D00, # .. 0x1D25 ; Latin 0x1D00, # .. 0x1D25 ; Latin
0x1D26, # .. 0x1D2A ; Greek 0x1D26, # .. 0x1D2A ; Greek
0x1D2B, # .. 0x1D2B ; Cyrillic 0x1D2B, # .. 0x1D2B ; Cyrillic
@ -672,10 +659,7 @@ RANGES = [
0x2B74, # .. 0x2B75 ; Unknown 0x2B74, # .. 0x2B75 ; Unknown
0x2B76, # .. 0x2B95 ; Common 0x2B76, # .. 0x2B95 ; Common
0x2B96, # .. 0x2B97 ; Unknown 0x2B96, # .. 0x2B97 ; Unknown
0x2B98, # .. 0x2BC8 ; Common 0x2B98, # .. 0x2BFF ; Common
0x2BC9, # .. 0x2BC9 ; Unknown
0x2BCA, # .. 0x2BFE ; Common
0x2BFF, # .. 0x2BFF ; Unknown
0x2C00, # .. 0x2C2E ; Glagolitic 0x2C00, # .. 0x2C2E ; Glagolitic
0x2C2F, # .. 0x2C2F ; Unknown 0x2C2F, # .. 0x2C2F ; Unknown
0x2C30, # .. 0x2C5E ; Glagolitic 0x2C30, # .. 0x2C5E ; Glagolitic
@ -714,8 +698,8 @@ RANGES = [
0x2DD8, # .. 0x2DDE ; Ethiopic 0x2DD8, # .. 0x2DDE ; Ethiopic
0x2DDF, # .. 0x2DDF ; Unknown 0x2DDF, # .. 0x2DDF ; Unknown
0x2DE0, # .. 0x2DFF ; Cyrillic 0x2DE0, # .. 0x2DFF ; Cyrillic
0x2E00, # .. 0x2E4E ; Common 0x2E00, # .. 0x2E4F ; Common
0x2E4F, # .. 0x2E7F ; Unknown 0x2E50, # .. 0x2E7F ; Unknown
0x2E80, # .. 0x2E99 ; Han 0x2E80, # .. 0x2E99 ; Han
0x2E9A, # .. 0x2E9A ; Unknown 0x2E9A, # .. 0x2E9A ; Unknown
0x2E9B, # .. 0x2EF3 ; Han 0x2E9B, # .. 0x2EF3 ; Han
@ -762,7 +746,7 @@ RANGES = [
0x3260, # .. 0x327E ; Hangul 0x3260, # .. 0x327E ; Hangul
0x327F, # .. 0x32CF ; Common 0x327F, # .. 0x32CF ; Common
0x32D0, # .. 0x32FE ; Katakana 0x32D0, # .. 0x32FE ; Katakana
0x32FF, # .. 0x32FF ; Unknown 0x32FF, # .. 0x32FF ; Common
0x3300, # .. 0x3357 ; Katakana 0x3300, # .. 0x3357 ; Katakana
0x3358, # .. 0x33FF ; Common 0x3358, # .. 0x33FF ; Common
0x3400, # .. 0x4DB5 ; Han 0x3400, # .. 0x4DB5 ; Han
@ -783,8 +767,10 @@ RANGES = [
0xA700, # .. 0xA721 ; Common 0xA700, # .. 0xA721 ; Common
0xA722, # .. 0xA787 ; Latin 0xA722, # .. 0xA787 ; Latin
0xA788, # .. 0xA78A ; Common 0xA788, # .. 0xA78A ; Common
0xA78B, # .. 0xA7B9 ; Latin 0xA78B, # .. 0xA7BF ; Latin
0xA7BA, # .. 0xA7F6 ; Unknown 0xA7C0, # .. 0xA7C1 ; Unknown
0xA7C2, # .. 0xA7C6 ; Latin
0xA7C7, # .. 0xA7F6 ; Unknown
0xA7F7, # .. 0xA7FF ; Latin 0xA7F7, # .. 0xA7FF ; Latin
0xA800, # .. 0xA82B ; Syloti_Nagri 0xA800, # .. 0xA82B ; Syloti_Nagri
0xA82C, # .. 0xA82F ; Unknown 0xA82C, # .. 0xA82F ; Unknown
@ -840,7 +826,8 @@ RANGES = [
0xAB5B, # .. 0xAB5B ; Common 0xAB5B, # .. 0xAB5B ; Common
0xAB5C, # .. 0xAB64 ; Latin 0xAB5C, # .. 0xAB64 ; Latin
0xAB65, # .. 0xAB65 ; Greek 0xAB65, # .. 0xAB65 ; Greek
0xAB66, # .. 0xAB6F ; Unknown 0xAB66, # .. 0xAB67 ; Latin
0xAB68, # .. 0xAB6F ; Unknown
0xAB70, # .. 0xABBF ; Cherokee 0xAB70, # .. 0xABBF ; Cherokee
0xABC0, # .. 0xABED ; Meetei_Mayek 0xABC0, # .. 0xABED ; Meetei_Mayek
0xABEE, # .. 0xABEF ; Unknown 0xABEE, # .. 0xABEF ; Unknown
@ -1086,7 +1073,9 @@ RANGES = [
0x10F00, # .. 0x10F27 ; Old_Sogdian 0x10F00, # .. 0x10F27 ; Old_Sogdian
0x10F28, # .. 0x10F2F ; Unknown 0x10F28, # .. 0x10F2F ; Unknown
0x10F30, # .. 0x10F59 ; Sogdian 0x10F30, # .. 0x10F59 ; Sogdian
0x10F5A, # .. 0x10FFF ; Unknown 0x10F5A, # .. 0x10FDF ; Unknown
0x10FE0, # .. 0x10FF6 ; Elymaic
0x10FF7, # .. 0x10FFF ; Unknown
0x11000, # .. 0x1104D ; Brahmi 0x11000, # .. 0x1104D ; Brahmi
0x1104E, # .. 0x11051 ; Unknown 0x1104E, # .. 0x11051 ; Unknown
0x11052, # .. 0x1106F ; Brahmi 0x11052, # .. 0x1106F ; Brahmi
@ -1165,8 +1154,8 @@ RANGES = [
0x1145A, # .. 0x1145A ; Unknown 0x1145A, # .. 0x1145A ; Unknown
0x1145B, # .. 0x1145B ; Newa 0x1145B, # .. 0x1145B ; Newa
0x1145C, # .. 0x1145C ; Unknown 0x1145C, # .. 0x1145C ; Unknown
0x1145D, # .. 0x1145E ; Newa 0x1145D, # .. 0x1145F ; Newa
0x1145F, # .. 0x1147F ; Unknown 0x11460, # .. 0x1147F ; Unknown
0x11480, # .. 0x114C7 ; Tirhuta 0x11480, # .. 0x114C7 ; Tirhuta
0x114C8, # .. 0x114CF ; Unknown 0x114C8, # .. 0x114CF ; Unknown
0x114D0, # .. 0x114D9 ; Tirhuta 0x114D0, # .. 0x114D9 ; Tirhuta
@ -1181,8 +1170,8 @@ RANGES = [
0x1165A, # .. 0x1165F ; Unknown 0x1165A, # .. 0x1165F ; Unknown
0x11660, # .. 0x1166C ; Mongolian 0x11660, # .. 0x1166C ; Mongolian
0x1166D, # .. 0x1167F ; Unknown 0x1166D, # .. 0x1167F ; Unknown
0x11680, # .. 0x116B7 ; Takri 0x11680, # .. 0x116B8 ; Takri
0x116B8, # .. 0x116BF ; Unknown 0x116B9, # .. 0x116BF ; Unknown
0x116C0, # .. 0x116C9 ; Takri 0x116C0, # .. 0x116C9 ; Takri
0x116CA, # .. 0x116FF ; Unknown 0x116CA, # .. 0x116FF ; Unknown
0x11700, # .. 0x1171A ; Ahom 0x11700, # .. 0x1171A ; Ahom
@ -1196,12 +1185,16 @@ RANGES = [
0x118A0, # .. 0x118F2 ; Warang_Citi 0x118A0, # .. 0x118F2 ; Warang_Citi
0x118F3, # .. 0x118FE ; Unknown 0x118F3, # .. 0x118FE ; Unknown
0x118FF, # .. 0x118FF ; Warang_Citi 0x118FF, # .. 0x118FF ; Warang_Citi
0x11900, # .. 0x119FF ; Unknown 0x11900, # .. 0x1199F ; Unknown
0x119A0, # .. 0x119A7 ; Nandinagari
0x119A8, # .. 0x119A9 ; Unknown
0x119AA, # .. 0x119D7 ; Nandinagari
0x119D8, # .. 0x119D9 ; Unknown
0x119DA, # .. 0x119E4 ; Nandinagari
0x119E5, # .. 0x119FF ; Unknown
0x11A00, # .. 0x11A47 ; Zanabazar_Square 0x11A00, # .. 0x11A47 ; Zanabazar_Square
0x11A48, # .. 0x11A4F ; Unknown 0x11A48, # .. 0x11A4F ; Unknown
0x11A50, # .. 0x11A83 ; Soyombo 0x11A50, # .. 0x11AA2 ; Soyombo
0x11A84, # .. 0x11A85 ; Unknown
0x11A86, # .. 0x11AA2 ; Soyombo
0x11AA3, # .. 0x11ABF ; Unknown 0x11AA3, # .. 0x11ABF ; Unknown
0x11AC0, # .. 0x11AF8 ; Pau_Cin_Hau 0x11AC0, # .. 0x11AF8 ; Pau_Cin_Hau
0x11AF9, # .. 0x11BFF ; Unknown 0x11AF9, # .. 0x11BFF ; Unknown
@ -1246,7 +1239,10 @@ RANGES = [
0x11DA0, # .. 0x11DA9 ; Gunjala_Gondi 0x11DA0, # .. 0x11DA9 ; Gunjala_Gondi
0x11DAA, # .. 0x11EDF ; Unknown 0x11DAA, # .. 0x11EDF ; Unknown
0x11EE0, # .. 0x11EF8 ; Makasar 0x11EE0, # .. 0x11EF8 ; Makasar
0x11EF9, # .. 0x11FFF ; Unknown 0x11EF9, # .. 0x11FBF ; Unknown
0x11FC0, # .. 0x11FF1 ; Tamil
0x11FF2, # .. 0x11FFE ; Unknown
0x11FFF, # .. 0x11FFF ; Tamil
0x12000, # .. 0x12399 ; Cuneiform 0x12000, # .. 0x12399 ; Cuneiform
0x1239A, # .. 0x123FF ; Unknown 0x1239A, # .. 0x123FF ; Unknown
0x12400, # .. 0x1246E ; Cuneiform 0x12400, # .. 0x1246E ; Cuneiform
@ -1256,7 +1252,9 @@ RANGES = [
0x12480, # .. 0x12543 ; Cuneiform 0x12480, # .. 0x12543 ; Cuneiform
0x12544, # .. 0x12FFF ; Unknown 0x12544, # .. 0x12FFF ; Unknown
0x13000, # .. 0x1342E ; Egyptian_Hieroglyphs 0x13000, # .. 0x1342E ; Egyptian_Hieroglyphs
0x1342F, # .. 0x143FF ; Unknown 0x1342F, # .. 0x1342F ; Unknown
0x13430, # .. 0x13438 ; Egyptian_Hieroglyphs
0x13439, # .. 0x143FF ; Unknown
0x14400, # .. 0x14646 ; Anatolian_Hieroglyphs 0x14400, # .. 0x14646 ; Anatolian_Hieroglyphs
0x14647, # .. 0x167FF ; Unknown 0x14647, # .. 0x167FF ; Unknown
0x16800, # .. 0x16A38 ; Bamum 0x16800, # .. 0x16A38 ; Bamum
@ -1283,22 +1281,27 @@ RANGES = [
0x16B90, # .. 0x16E3F ; Unknown 0x16B90, # .. 0x16E3F ; Unknown
0x16E40, # .. 0x16E9A ; Medefaidrin 0x16E40, # .. 0x16E9A ; Medefaidrin
0x16E9B, # .. 0x16EFF ; Unknown 0x16E9B, # .. 0x16EFF ; Unknown
0x16F00, # .. 0x16F44 ; Miao 0x16F00, # .. 0x16F4A ; Miao
0x16F45, # .. 0x16F4F ; Unknown 0x16F4B, # .. 0x16F4E ; Unknown
0x16F50, # .. 0x16F7E ; Miao 0x16F4F, # .. 0x16F87 ; Miao
0x16F7F, # .. 0x16F8E ; Unknown 0x16F88, # .. 0x16F8E ; Unknown
0x16F8F, # .. 0x16F9F ; Miao 0x16F8F, # .. 0x16F9F ; Miao
0x16FA0, # .. 0x16FDF ; Unknown 0x16FA0, # .. 0x16FDF ; Unknown
0x16FE0, # .. 0x16FE0 ; Tangut 0x16FE0, # .. 0x16FE0 ; Tangut
0x16FE1, # .. 0x16FE1 ; Nushu 0x16FE1, # .. 0x16FE1 ; Nushu
0x16FE2, # .. 0x16FFF ; Unknown 0x16FE2, # .. 0x16FE3 ; Common
0x17000, # .. 0x187F1 ; Tangut 0x16FE4, # .. 0x16FFF ; Unknown
0x187F2, # .. 0x187FF ; Unknown 0x17000, # .. 0x187F7 ; Tangut
0x187F8, # .. 0x187FF ; Unknown
0x18800, # .. 0x18AF2 ; Tangut 0x18800, # .. 0x18AF2 ; Tangut
0x18AF3, # .. 0x1AFFF ; Unknown 0x18AF3, # .. 0x1AFFF ; Unknown
0x1B000, # .. 0x1B000 ; Katakana 0x1B000, # .. 0x1B000 ; Katakana
0x1B001, # .. 0x1B11E ; Hiragana 0x1B001, # .. 0x1B11E ; Hiragana
0x1B11F, # .. 0x1B16F ; Unknown 0x1B11F, # .. 0x1B14F ; Unknown
0x1B150, # .. 0x1B152 ; Hiragana
0x1B153, # .. 0x1B163 ; Unknown
0x1B164, # .. 0x1B167 ; Katakana
0x1B168, # .. 0x1B16F ; Unknown
0x1B170, # .. 0x1B2FB ; Nushu 0x1B170, # .. 0x1B2FB ; Nushu
0x1B2FC, # .. 0x1BBFF ; Unknown 0x1B2FC, # .. 0x1BBFF ; Unknown
0x1BC00, # .. 0x1BC6A ; Duployan 0x1BC00, # .. 0x1BC6A ; Duployan
@ -1390,19 +1393,33 @@ RANGES = [
0x1E023, # .. 0x1E024 ; Glagolitic 0x1E023, # .. 0x1E024 ; Glagolitic
0x1E025, # .. 0x1E025 ; Unknown 0x1E025, # .. 0x1E025 ; Unknown
0x1E026, # .. 0x1E02A ; Glagolitic 0x1E026, # .. 0x1E02A ; Glagolitic
0x1E02B, # .. 0x1E7FF ; Unknown 0x1E02B, # .. 0x1E0FF ; Unknown
0x1E100, # .. 0x1E12C ; Nyiakeng_Puachue_Hmong
0x1E12D, # .. 0x1E12F ; Unknown
0x1E130, # .. 0x1E13D ; Nyiakeng_Puachue_Hmong
0x1E13E, # .. 0x1E13F ; Unknown
0x1E140, # .. 0x1E149 ; Nyiakeng_Puachue_Hmong
0x1E14A, # .. 0x1E14D ; Unknown
0x1E14E, # .. 0x1E14F ; Nyiakeng_Puachue_Hmong
0x1E150, # .. 0x1E2BF ; Unknown
0x1E2C0, # .. 0x1E2F9 ; Wancho
0x1E2FA, # .. 0x1E2FE ; Unknown
0x1E2FF, # .. 0x1E2FF ; Wancho
0x1E300, # .. 0x1E7FF ; Unknown
0x1E800, # .. 0x1E8C4 ; Mende_Kikakui 0x1E800, # .. 0x1E8C4 ; Mende_Kikakui
0x1E8C5, # .. 0x1E8C6 ; Unknown 0x1E8C5, # .. 0x1E8C6 ; Unknown
0x1E8C7, # .. 0x1E8D6 ; Mende_Kikakui 0x1E8C7, # .. 0x1E8D6 ; Mende_Kikakui
0x1E8D7, # .. 0x1E8FF ; Unknown 0x1E8D7, # .. 0x1E8FF ; Unknown
0x1E900, # .. 0x1E94A ; Adlam 0x1E900, # .. 0x1E94B ; Adlam
0x1E94B, # .. 0x1E94F ; Unknown 0x1E94C, # .. 0x1E94F ; Unknown
0x1E950, # .. 0x1E959 ; Adlam 0x1E950, # .. 0x1E959 ; Adlam
0x1E95A, # .. 0x1E95D ; Unknown 0x1E95A, # .. 0x1E95D ; Unknown
0x1E95E, # .. 0x1E95F ; Adlam 0x1E95E, # .. 0x1E95F ; Adlam
0x1E960, # .. 0x1EC70 ; Unknown 0x1E960, # .. 0x1EC70 ; Unknown
0x1EC71, # .. 0x1ECB4 ; Common 0x1EC71, # .. 0x1ECB4 ; Common
0x1ECB5, # .. 0x1EDFF ; Unknown 0x1ECB5, # .. 0x1ED00 ; Unknown
0x1ED01, # .. 0x1ED3D ; Common
0x1ED3E, # .. 0x1EDFF ; Unknown
0x1EE00, # .. 0x1EE03 ; Arabic 0x1EE00, # .. 0x1EE03 ; Arabic
0x1EE04, # .. 0x1EE04 ; Unknown 0x1EE04, # .. 0x1EE04 ; Unknown
0x1EE05, # .. 0x1EE1F ; Arabic 0x1EE05, # .. 0x1EE1F ; Arabic
@ -1485,8 +1502,8 @@ RANGES = [
0x1F0F6, # .. 0x1F0FF ; Unknown 0x1F0F6, # .. 0x1F0FF ; Unknown
0x1F100, # .. 0x1F10C ; Common 0x1F100, # .. 0x1F10C ; Common
0x1F10D, # .. 0x1F10F ; Unknown 0x1F10D, # .. 0x1F10F ; Unknown
0x1F110, # .. 0x1F16B ; Common 0x1F110, # .. 0x1F16C ; Common
0x1F16C, # .. 0x1F16F ; Unknown 0x1F16D, # .. 0x1F16F ; Unknown
0x1F170, # .. 0x1F1AC ; Common 0x1F170, # .. 0x1F1AC ; Common
0x1F1AD, # .. 0x1F1E5 ; Unknown 0x1F1AD, # .. 0x1F1E5 ; Unknown
0x1F1E6, # .. 0x1F1FF ; Common 0x1F1E6, # .. 0x1F1FF ; Common
@ -1501,16 +1518,18 @@ RANGES = [
0x1F252, # .. 0x1F25F ; Unknown 0x1F252, # .. 0x1F25F ; Unknown
0x1F260, # .. 0x1F265 ; Common 0x1F260, # .. 0x1F265 ; Common
0x1F266, # .. 0x1F2FF ; Unknown 0x1F266, # .. 0x1F2FF ; Unknown
0x1F300, # .. 0x1F6D4 ; Common 0x1F300, # .. 0x1F6D5 ; Common
0x1F6D5, # .. 0x1F6DF ; Unknown 0x1F6D6, # .. 0x1F6DF ; Unknown
0x1F6E0, # .. 0x1F6EC ; Common 0x1F6E0, # .. 0x1F6EC ; Common
0x1F6ED, # .. 0x1F6EF ; Unknown 0x1F6ED, # .. 0x1F6EF ; Unknown
0x1F6F0, # .. 0x1F6F9 ; Common 0x1F6F0, # .. 0x1F6FA ; Common
0x1F6FA, # .. 0x1F6FF ; Unknown 0x1F6FB, # .. 0x1F6FF ; Unknown
0x1F700, # .. 0x1F773 ; Common 0x1F700, # .. 0x1F773 ; Common
0x1F774, # .. 0x1F77F ; Unknown 0x1F774, # .. 0x1F77F ; Unknown
0x1F780, # .. 0x1F7D8 ; Common 0x1F780, # .. 0x1F7D8 ; Common
0x1F7D9, # .. 0x1F7FF ; Unknown 0x1F7D9, # .. 0x1F7DF ; Unknown
0x1F7E0, # .. 0x1F7EB ; Common
0x1F7EC, # .. 0x1F7FF ; Unknown
0x1F800, # .. 0x1F80B ; Common 0x1F800, # .. 0x1F80B ; Common
0x1F80C, # .. 0x1F80F ; Unknown 0x1F80C, # .. 0x1F80F ; Unknown
0x1F810, # .. 0x1F847 ; Common 0x1F810, # .. 0x1F847 ; Common
@ -1522,25 +1541,29 @@ RANGES = [
0x1F890, # .. 0x1F8AD ; Common 0x1F890, # .. 0x1F8AD ; Common
0x1F8AE, # .. 0x1F8FF ; Unknown 0x1F8AE, # .. 0x1F8FF ; Unknown
0x1F900, # .. 0x1F90B ; Common 0x1F900, # .. 0x1F90B ; Common
0x1F90C, # .. 0x1F90F ; Unknown 0x1F90C, # .. 0x1F90C ; Unknown
0x1F910, # .. 0x1F93E ; Common 0x1F90D, # .. 0x1F971 ; Common
0x1F93F, # .. 0x1F93F ; Unknown 0x1F972, # .. 0x1F972 ; Unknown
0x1F940, # .. 0x1F970 ; Common
0x1F971, # .. 0x1F972 ; Unknown
0x1F973, # .. 0x1F976 ; Common 0x1F973, # .. 0x1F976 ; Common
0x1F977, # .. 0x1F979 ; Unknown 0x1F977, # .. 0x1F979 ; Unknown
0x1F97A, # .. 0x1F97A ; Common 0x1F97A, # .. 0x1F9A2 ; Common
0x1F97B, # .. 0x1F97B ; Unknown 0x1F9A3, # .. 0x1F9A4 ; Unknown
0x1F97C, # .. 0x1F9A2 ; Common 0x1F9A5, # .. 0x1F9AA ; Common
0x1F9A3, # .. 0x1F9AF ; Unknown 0x1F9AB, # .. 0x1F9AD ; Unknown
0x1F9B0, # .. 0x1F9B9 ; Common 0x1F9AE, # .. 0x1F9CA ; Common
0x1F9BA, # .. 0x1F9BF ; Unknown 0x1F9CB, # .. 0x1F9CC ; Unknown
0x1F9C0, # .. 0x1F9C2 ; Common 0x1F9CD, # .. 0x1FA53 ; Common
0x1F9C3, # .. 0x1F9CF ; Unknown 0x1FA54, # .. 0x1FA5F ; Unknown
0x1F9D0, # .. 0x1F9FF ; Common
0x1FA00, # .. 0x1FA5F ; Unknown
0x1FA60, # .. 0x1FA6D ; Common 0x1FA60, # .. 0x1FA6D ; Common
0x1FA6E, # .. 0x1FFFF ; Unknown 0x1FA6E, # .. 0x1FA6F ; Unknown
0x1FA70, # .. 0x1FA73 ; Common
0x1FA74, # .. 0x1FA77 ; Unknown
0x1FA78, # .. 0x1FA7A ; Common
0x1FA7B, # .. 0x1FA7F ; Unknown
0x1FA80, # .. 0x1FA82 ; Common
0x1FA83, # .. 0x1FA8F ; Unknown
0x1FA90, # .. 0x1FA95 ; Common
0x1FA96, # .. 0x1FFFF ; Unknown
0x20000, # .. 0x2A6D6 ; Han 0x20000, # .. 0x2A6D6 ; Han
0x2A6D7, # .. 0x2A6FF ; Unknown 0x2A6D7, # .. 0x2A6FF ; Unknown
0x2A700, # .. 0x2B734 ; Han 0x2A700, # .. 0x2B734 ; Han
@ -1669,8 +1692,8 @@ VALUES = [
'Zyyy', # 08E2..08E2 ; Common 'Zyyy', # 08E2..08E2 ; Common
'Arab', # 08E3..08FF ; Arabic 'Arab', # 08E3..08FF ; Arabic
'Deva', # 0900..0950 ; Devanagari 'Deva', # 0900..0950 ; Devanagari
'Zinh', # 0951..0952 ; Inherited 'Zinh', # 0951..0954 ; Inherited
'Deva', # 0953..0963 ; Devanagari 'Deva', # 0955..0963 ; Devanagari
'Zyyy', # 0964..0965 ; Common 'Zyyy', # 0964..0965 ; Common
'Deva', # 0966..097F ; Devanagari 'Deva', # 0966..097F ; Devanagari
'Beng', # 0980..0983 ; Bengali 'Beng', # 0980..0983 ; Bengali
@ -1842,8 +1865,8 @@ VALUES = [
'Telu', # 0C60..0C63 ; Telugu 'Telu', # 0C60..0C63 ; Telugu
'Zzzz', # 0C64..0C65 ; Unknown 'Zzzz', # 0C64..0C65 ; Unknown
'Telu', # 0C66..0C6F ; Telugu 'Telu', # 0C66..0C6F ; Telugu
'Zzzz', # 0C70..0C77 ; Unknown 'Zzzz', # 0C70..0C76 ; Unknown
'Telu', # 0C78..0C7F ; Telugu 'Telu', # 0C77..0C7F ; Telugu
'Knda', # 0C80..0C8C ; Kannada 'Knda', # 0C80..0C8C ; Kannada
'Zzzz', # 0C8D..0C8D ; Unknown 'Zzzz', # 0C8D..0C8D ; Unknown
'Knda', # 0C8E..0C90 ; Kannada 'Knda', # 0C8E..0C90 ; Kannada
@ -1918,28 +1941,14 @@ VALUES = [
'Laoo', # 0E81..0E82 ; Lao 'Laoo', # 0E81..0E82 ; Lao
'Zzzz', # 0E83..0E83 ; Unknown 'Zzzz', # 0E83..0E83 ; Unknown
'Laoo', # 0E84..0E84 ; Lao 'Laoo', # 0E84..0E84 ; Lao
'Zzzz', # 0E85..0E86 ; Unknown 'Zzzz', # 0E85..0E85 ; Unknown
'Laoo', # 0E87..0E88 ; Lao 'Laoo', # 0E86..0E8A ; Lao
'Zzzz', # 0E89..0E89 ; Unknown 'Zzzz', # 0E8B..0E8B ; Unknown
'Laoo', # 0E8A..0E8A ; Lao 'Laoo', # 0E8C..0EA3 ; Lao
'Zzzz', # 0E8B..0E8C ; Unknown
'Laoo', # 0E8D..0E8D ; Lao
'Zzzz', # 0E8E..0E93 ; Unknown
'Laoo', # 0E94..0E97 ; Lao
'Zzzz', # 0E98..0E98 ; Unknown
'Laoo', # 0E99..0E9F ; Lao
'Zzzz', # 0EA0..0EA0 ; Unknown
'Laoo', # 0EA1..0EA3 ; Lao
'Zzzz', # 0EA4..0EA4 ; Unknown 'Zzzz', # 0EA4..0EA4 ; Unknown
'Laoo', # 0EA5..0EA5 ; Lao 'Laoo', # 0EA5..0EA5 ; Lao
'Zzzz', # 0EA6..0EA6 ; Unknown 'Zzzz', # 0EA6..0EA6 ; Unknown
'Laoo', # 0EA7..0EA7 ; Lao 'Laoo', # 0EA7..0EBD ; Lao
'Zzzz', # 0EA8..0EA9 ; Unknown
'Laoo', # 0EAA..0EAB ; Lao
'Zzzz', # 0EAC..0EAC ; Unknown
'Laoo', # 0EAD..0EB9 ; Lao
'Zzzz', # 0EBA..0EBA ; Unknown
'Laoo', # 0EBB..0EBD ; Lao
'Zzzz', # 0EBE..0EBF ; Unknown 'Zzzz', # 0EBE..0EBF ; Unknown
'Laoo', # 0EC0..0EC4 ; Lao 'Laoo', # 0EC0..0EC4 ; Lao
'Zzzz', # 0EC5..0EC5 ; Unknown 'Zzzz', # 0EC5..0EC5 ; Unknown
@ -2126,7 +2135,8 @@ VALUES = [
'Zinh', # 1CF4..1CF4 ; Inherited 'Zinh', # 1CF4..1CF4 ; Inherited
'Zyyy', # 1CF5..1CF7 ; Common 'Zyyy', # 1CF5..1CF7 ; Common
'Zinh', # 1CF8..1CF9 ; Inherited 'Zinh', # 1CF8..1CF9 ; Inherited
'Zzzz', # 1CFA..1CFF ; Unknown 'Zyyy', # 1CFA..1CFA ; Common
'Zzzz', # 1CFB..1CFF ; Unknown
'Latn', # 1D00..1D25 ; Latin 'Latn', # 1D00..1D25 ; Latin
'Grek', # 1D26..1D2A ; Greek 'Grek', # 1D26..1D2A ; Greek
'Cyrl', # 1D2B..1D2B ; Cyrillic 'Cyrl', # 1D2B..1D2B ; Cyrillic
@ -2213,10 +2223,7 @@ VALUES = [
'Zzzz', # 2B74..2B75 ; Unknown 'Zzzz', # 2B74..2B75 ; Unknown
'Zyyy', # 2B76..2B95 ; Common 'Zyyy', # 2B76..2B95 ; Common
'Zzzz', # 2B96..2B97 ; Unknown 'Zzzz', # 2B96..2B97 ; Unknown
'Zyyy', # 2B98..2BC8 ; Common 'Zyyy', # 2B98..2BFF ; Common
'Zzzz', # 2BC9..2BC9 ; Unknown
'Zyyy', # 2BCA..2BFE ; Common
'Zzzz', # 2BFF..2BFF ; Unknown
'Glag', # 2C00..2C2E ; Glagolitic 'Glag', # 2C00..2C2E ; Glagolitic
'Zzzz', # 2C2F..2C2F ; Unknown 'Zzzz', # 2C2F..2C2F ; Unknown
'Glag', # 2C30..2C5E ; Glagolitic 'Glag', # 2C30..2C5E ; Glagolitic
@ -2255,8 +2262,8 @@ VALUES = [
'Ethi', # 2DD8..2DDE ; Ethiopic 'Ethi', # 2DD8..2DDE ; Ethiopic
'Zzzz', # 2DDF..2DDF ; Unknown 'Zzzz', # 2DDF..2DDF ; Unknown
'Cyrl', # 2DE0..2DFF ; Cyrillic 'Cyrl', # 2DE0..2DFF ; Cyrillic
'Zyyy', # 2E00..2E4E ; Common 'Zyyy', # 2E00..2E4F ; Common
'Zzzz', # 2E4F..2E7F ; Unknown 'Zzzz', # 2E50..2E7F ; Unknown
'Hani', # 2E80..2E99 ; Han 'Hani', # 2E80..2E99 ; Han
'Zzzz', # 2E9A..2E9A ; Unknown 'Zzzz', # 2E9A..2E9A ; Unknown
'Hani', # 2E9B..2EF3 ; Han 'Hani', # 2E9B..2EF3 ; Han
@ -2303,7 +2310,7 @@ VALUES = [
'Hang', # 3260..327E ; Hangul 'Hang', # 3260..327E ; Hangul
'Zyyy', # 327F..32CF ; Common 'Zyyy', # 327F..32CF ; Common
'Kana', # 32D0..32FE ; Katakana 'Kana', # 32D0..32FE ; Katakana
'Zzzz', # 32FF..32FF ; Unknown 'Zyyy', # 32FF..32FF ; Common
'Kana', # 3300..3357 ; Katakana 'Kana', # 3300..3357 ; Katakana
'Zyyy', # 3358..33FF ; Common 'Zyyy', # 3358..33FF ; Common
'Hani', # 3400..4DB5 ; Han 'Hani', # 3400..4DB5 ; Han
@ -2324,8 +2331,10 @@ VALUES = [
'Zyyy', # A700..A721 ; Common 'Zyyy', # A700..A721 ; Common
'Latn', # A722..A787 ; Latin 'Latn', # A722..A787 ; Latin
'Zyyy', # A788..A78A ; Common 'Zyyy', # A788..A78A ; Common
'Latn', # A78B..A7B9 ; Latin 'Latn', # A78B..A7BF ; Latin
'Zzzz', # A7BA..A7F6 ; Unknown 'Zzzz', # A7C0..A7C1 ; Unknown
'Latn', # A7C2..A7C6 ; Latin
'Zzzz', # A7C7..A7F6 ; Unknown
'Latn', # A7F7..A7FF ; Latin 'Latn', # A7F7..A7FF ; Latin
'Sylo', # A800..A82B ; Syloti_Nagri 'Sylo', # A800..A82B ; Syloti_Nagri
'Zzzz', # A82C..A82F ; Unknown 'Zzzz', # A82C..A82F ; Unknown
@ -2381,7 +2390,8 @@ VALUES = [
'Zyyy', # AB5B..AB5B ; Common 'Zyyy', # AB5B..AB5B ; Common
'Latn', # AB5C..AB64 ; Latin 'Latn', # AB5C..AB64 ; Latin
'Grek', # AB65..AB65 ; Greek 'Grek', # AB65..AB65 ; Greek
'Zzzz', # AB66..AB6F ; Unknown 'Latn', # AB66..AB67 ; Latin
'Zzzz', # AB68..AB6F ; Unknown
'Cher', # AB70..ABBF ; Cherokee 'Cher', # AB70..ABBF ; Cherokee
'Mtei', # ABC0..ABED ; Meetei_Mayek 'Mtei', # ABC0..ABED ; Meetei_Mayek
'Zzzz', # ABEE..ABEF ; Unknown 'Zzzz', # ABEE..ABEF ; Unknown
@ -2627,7 +2637,9 @@ VALUES = [
'Sogo', # 10F00..10F27 ; Old_Sogdian 'Sogo', # 10F00..10F27 ; Old_Sogdian
'Zzzz', # 10F28..10F2F ; Unknown 'Zzzz', # 10F28..10F2F ; Unknown
'Sogd', # 10F30..10F59 ; Sogdian 'Sogd', # 10F30..10F59 ; Sogdian
'Zzzz', # 10F5A..10FFF ; Unknown 'Zzzz', # 10F5A..10FDF ; Unknown
'Elym', # 10FE0..10FF6 ; Elymaic
'Zzzz', # 10FF7..10FFF ; Unknown
'Brah', # 11000..1104D ; Brahmi 'Brah', # 11000..1104D ; Brahmi
'Zzzz', # 1104E..11051 ; Unknown 'Zzzz', # 1104E..11051 ; Unknown
'Brah', # 11052..1106F ; Brahmi 'Brah', # 11052..1106F ; Brahmi
@ -2706,8 +2718,8 @@ VALUES = [
'Zzzz', # 1145A..1145A ; Unknown 'Zzzz', # 1145A..1145A ; Unknown
'Newa', # 1145B..1145B ; Newa 'Newa', # 1145B..1145B ; Newa
'Zzzz', # 1145C..1145C ; Unknown 'Zzzz', # 1145C..1145C ; Unknown
'Newa', # 1145D..1145E ; Newa 'Newa', # 1145D..1145F ; Newa
'Zzzz', # 1145F..1147F ; Unknown 'Zzzz', # 11460..1147F ; Unknown
'Tirh', # 11480..114C7 ; Tirhuta 'Tirh', # 11480..114C7 ; Tirhuta
'Zzzz', # 114C8..114CF ; Unknown 'Zzzz', # 114C8..114CF ; Unknown
'Tirh', # 114D0..114D9 ; Tirhuta 'Tirh', # 114D0..114D9 ; Tirhuta
@ -2722,8 +2734,8 @@ VALUES = [
'Zzzz', # 1165A..1165F ; Unknown 'Zzzz', # 1165A..1165F ; Unknown
'Mong', # 11660..1166C ; Mongolian 'Mong', # 11660..1166C ; Mongolian
'Zzzz', # 1166D..1167F ; Unknown 'Zzzz', # 1166D..1167F ; Unknown
'Takr', # 11680..116B7 ; Takri 'Takr', # 11680..116B8 ; Takri
'Zzzz', # 116B8..116BF ; Unknown 'Zzzz', # 116B9..116BF ; Unknown
'Takr', # 116C0..116C9 ; Takri 'Takr', # 116C0..116C9 ; Takri
'Zzzz', # 116CA..116FF ; Unknown 'Zzzz', # 116CA..116FF ; Unknown
'Ahom', # 11700..1171A ; Ahom 'Ahom', # 11700..1171A ; Ahom
@ -2737,12 +2749,16 @@ VALUES = [
'Wara', # 118A0..118F2 ; Warang_Citi 'Wara', # 118A0..118F2 ; Warang_Citi
'Zzzz', # 118F3..118FE ; Unknown 'Zzzz', # 118F3..118FE ; Unknown
'Wara', # 118FF..118FF ; Warang_Citi 'Wara', # 118FF..118FF ; Warang_Citi
'Zzzz', # 11900..119FF ; Unknown 'Zzzz', # 11900..1199F ; Unknown
'Nand', # 119A0..119A7 ; Nandinagari
'Zzzz', # 119A8..119A9 ; Unknown
'Nand', # 119AA..119D7 ; Nandinagari
'Zzzz', # 119D8..119D9 ; Unknown
'Nand', # 119DA..119E4 ; Nandinagari
'Zzzz', # 119E5..119FF ; Unknown
'Zanb', # 11A00..11A47 ; Zanabazar_Square 'Zanb', # 11A00..11A47 ; Zanabazar_Square
'Zzzz', # 11A48..11A4F ; Unknown 'Zzzz', # 11A48..11A4F ; Unknown
'Soyo', # 11A50..11A83 ; Soyombo 'Soyo', # 11A50..11AA2 ; Soyombo
'Zzzz', # 11A84..11A85 ; Unknown
'Soyo', # 11A86..11AA2 ; Soyombo
'Zzzz', # 11AA3..11ABF ; Unknown 'Zzzz', # 11AA3..11ABF ; Unknown
'Pauc', # 11AC0..11AF8 ; Pau_Cin_Hau 'Pauc', # 11AC0..11AF8 ; Pau_Cin_Hau
'Zzzz', # 11AF9..11BFF ; Unknown 'Zzzz', # 11AF9..11BFF ; Unknown
@ -2787,7 +2803,10 @@ VALUES = [
'Gong', # 11DA0..11DA9 ; Gunjala_Gondi 'Gong', # 11DA0..11DA9 ; Gunjala_Gondi
'Zzzz', # 11DAA..11EDF ; Unknown 'Zzzz', # 11DAA..11EDF ; Unknown
'Maka', # 11EE0..11EF8 ; Makasar 'Maka', # 11EE0..11EF8 ; Makasar
'Zzzz', # 11EF9..11FFF ; Unknown 'Zzzz', # 11EF9..11FBF ; Unknown
'Taml', # 11FC0..11FF1 ; Tamil
'Zzzz', # 11FF2..11FFE ; Unknown
'Taml', # 11FFF..11FFF ; Tamil
'Xsux', # 12000..12399 ; Cuneiform 'Xsux', # 12000..12399 ; Cuneiform
'Zzzz', # 1239A..123FF ; Unknown 'Zzzz', # 1239A..123FF ; Unknown
'Xsux', # 12400..1246E ; Cuneiform 'Xsux', # 12400..1246E ; Cuneiform
@ -2797,7 +2816,9 @@ VALUES = [
'Xsux', # 12480..12543 ; Cuneiform 'Xsux', # 12480..12543 ; Cuneiform
'Zzzz', # 12544..12FFF ; Unknown 'Zzzz', # 12544..12FFF ; Unknown
'Egyp', # 13000..1342E ; Egyptian_Hieroglyphs 'Egyp', # 13000..1342E ; Egyptian_Hieroglyphs
'Zzzz', # 1342F..143FF ; Unknown 'Zzzz', # 1342F..1342F ; Unknown
'Egyp', # 13430..13438 ; Egyptian_Hieroglyphs
'Zzzz', # 13439..143FF ; Unknown
'Hluw', # 14400..14646 ; Anatolian_Hieroglyphs 'Hluw', # 14400..14646 ; Anatolian_Hieroglyphs
'Zzzz', # 14647..167FF ; Unknown 'Zzzz', # 14647..167FF ; Unknown
'Bamu', # 16800..16A38 ; Bamum 'Bamu', # 16800..16A38 ; Bamum
@ -2824,22 +2845,27 @@ VALUES = [
'Zzzz', # 16B90..16E3F ; Unknown 'Zzzz', # 16B90..16E3F ; Unknown
'Medf', # 16E40..16E9A ; Medefaidrin 'Medf', # 16E40..16E9A ; Medefaidrin
'Zzzz', # 16E9B..16EFF ; Unknown 'Zzzz', # 16E9B..16EFF ; Unknown
'Plrd', # 16F00..16F44 ; Miao 'Plrd', # 16F00..16F4A ; Miao
'Zzzz', # 16F45..16F4F ; Unknown 'Zzzz', # 16F4B..16F4E ; Unknown
'Plrd', # 16F50..16F7E ; Miao 'Plrd', # 16F4F..16F87 ; Miao
'Zzzz', # 16F7F..16F8E ; Unknown 'Zzzz', # 16F88..16F8E ; Unknown
'Plrd', # 16F8F..16F9F ; Miao 'Plrd', # 16F8F..16F9F ; Miao
'Zzzz', # 16FA0..16FDF ; Unknown 'Zzzz', # 16FA0..16FDF ; Unknown
'Tang', # 16FE0..16FE0 ; Tangut 'Tang', # 16FE0..16FE0 ; Tangut
'Nshu', # 16FE1..16FE1 ; Nushu 'Nshu', # 16FE1..16FE1 ; Nushu
'Zzzz', # 16FE2..16FFF ; Unknown 'Zyyy', # 16FE2..16FE3 ; Common
'Tang', # 17000..187F1 ; Tangut 'Zzzz', # 16FE4..16FFF ; Unknown
'Zzzz', # 187F2..187FF ; Unknown 'Tang', # 17000..187F7 ; Tangut
'Zzzz', # 187F8..187FF ; Unknown
'Tang', # 18800..18AF2 ; Tangut 'Tang', # 18800..18AF2 ; Tangut
'Zzzz', # 18AF3..1AFFF ; Unknown 'Zzzz', # 18AF3..1AFFF ; Unknown
'Kana', # 1B000..1B000 ; Katakana 'Kana', # 1B000..1B000 ; Katakana
'Hira', # 1B001..1B11E ; Hiragana 'Hira', # 1B001..1B11E ; Hiragana
'Zzzz', # 1B11F..1B16F ; Unknown 'Zzzz', # 1B11F..1B14F ; Unknown
'Hira', # 1B150..1B152 ; Hiragana
'Zzzz', # 1B153..1B163 ; Unknown
'Kana', # 1B164..1B167 ; Katakana
'Zzzz', # 1B168..1B16F ; Unknown
'Nshu', # 1B170..1B2FB ; Nushu 'Nshu', # 1B170..1B2FB ; Nushu
'Zzzz', # 1B2FC..1BBFF ; Unknown 'Zzzz', # 1B2FC..1BBFF ; Unknown
'Dupl', # 1BC00..1BC6A ; Duployan 'Dupl', # 1BC00..1BC6A ; Duployan
@ -2931,19 +2957,33 @@ VALUES = [
'Glag', # 1E023..1E024 ; Glagolitic 'Glag', # 1E023..1E024 ; Glagolitic
'Zzzz', # 1E025..1E025 ; Unknown 'Zzzz', # 1E025..1E025 ; Unknown
'Glag', # 1E026..1E02A ; Glagolitic 'Glag', # 1E026..1E02A ; Glagolitic
'Zzzz', # 1E02B..1E7FF ; Unknown 'Zzzz', # 1E02B..1E0FF ; Unknown
'Hmnp', # 1E100..1E12C ; Nyiakeng_Puachue_Hmong
'Zzzz', # 1E12D..1E12F ; Unknown
'Hmnp', # 1E130..1E13D ; Nyiakeng_Puachue_Hmong
'Zzzz', # 1E13E..1E13F ; Unknown
'Hmnp', # 1E140..1E149 ; Nyiakeng_Puachue_Hmong
'Zzzz', # 1E14A..1E14D ; Unknown
'Hmnp', # 1E14E..1E14F ; Nyiakeng_Puachue_Hmong
'Zzzz', # 1E150..1E2BF ; Unknown
'Wcho', # 1E2C0..1E2F9 ; Wancho
'Zzzz', # 1E2FA..1E2FE ; Unknown
'Wcho', # 1E2FF..1E2FF ; Wancho
'Zzzz', # 1E300..1E7FF ; Unknown
'Mend', # 1E800..1E8C4 ; Mende_Kikakui 'Mend', # 1E800..1E8C4 ; Mende_Kikakui
'Zzzz', # 1E8C5..1E8C6 ; Unknown 'Zzzz', # 1E8C5..1E8C6 ; Unknown
'Mend', # 1E8C7..1E8D6 ; Mende_Kikakui 'Mend', # 1E8C7..1E8D6 ; Mende_Kikakui
'Zzzz', # 1E8D7..1E8FF ; Unknown 'Zzzz', # 1E8D7..1E8FF ; Unknown
'Adlm', # 1E900..1E94A ; Adlam 'Adlm', # 1E900..1E94B ; Adlam
'Zzzz', # 1E94B..1E94F ; Unknown 'Zzzz', # 1E94C..1E94F ; Unknown
'Adlm', # 1E950..1E959 ; Adlam 'Adlm', # 1E950..1E959 ; Adlam
'Zzzz', # 1E95A..1E95D ; Unknown 'Zzzz', # 1E95A..1E95D ; Unknown
'Adlm', # 1E95E..1E95F ; Adlam 'Adlm', # 1E95E..1E95F ; Adlam
'Zzzz', # 1E960..1EC70 ; Unknown 'Zzzz', # 1E960..1EC70 ; Unknown
'Zyyy', # 1EC71..1ECB4 ; Common 'Zyyy', # 1EC71..1ECB4 ; Common
'Zzzz', # 1ECB5..1EDFF ; Unknown 'Zzzz', # 1ECB5..1ED00 ; Unknown
'Zyyy', # 1ED01..1ED3D ; Common
'Zzzz', # 1ED3E..1EDFF ; Unknown
'Arab', # 1EE00..1EE03 ; Arabic 'Arab', # 1EE00..1EE03 ; Arabic
'Zzzz', # 1EE04..1EE04 ; Unknown 'Zzzz', # 1EE04..1EE04 ; Unknown
'Arab', # 1EE05..1EE1F ; Arabic 'Arab', # 1EE05..1EE1F ; Arabic
@ -3026,8 +3066,8 @@ VALUES = [
'Zzzz', # 1F0F6..1F0FF ; Unknown 'Zzzz', # 1F0F6..1F0FF ; Unknown
'Zyyy', # 1F100..1F10C ; Common 'Zyyy', # 1F100..1F10C ; Common
'Zzzz', # 1F10D..1F10F ; Unknown 'Zzzz', # 1F10D..1F10F ; Unknown
'Zyyy', # 1F110..1F16B ; Common 'Zyyy', # 1F110..1F16C ; Common
'Zzzz', # 1F16C..1F16F ; Unknown 'Zzzz', # 1F16D..1F16F ; Unknown
'Zyyy', # 1F170..1F1AC ; Common 'Zyyy', # 1F170..1F1AC ; Common
'Zzzz', # 1F1AD..1F1E5 ; Unknown 'Zzzz', # 1F1AD..1F1E5 ; Unknown
'Zyyy', # 1F1E6..1F1FF ; Common 'Zyyy', # 1F1E6..1F1FF ; Common
@ -3042,16 +3082,18 @@ VALUES = [
'Zzzz', # 1F252..1F25F ; Unknown 'Zzzz', # 1F252..1F25F ; Unknown
'Zyyy', # 1F260..1F265 ; Common 'Zyyy', # 1F260..1F265 ; Common
'Zzzz', # 1F266..1F2FF ; Unknown 'Zzzz', # 1F266..1F2FF ; Unknown
'Zyyy', # 1F300..1F6D4 ; Common 'Zyyy', # 1F300..1F6D5 ; Common
'Zzzz', # 1F6D5..1F6DF ; Unknown 'Zzzz', # 1F6D6..1F6DF ; Unknown
'Zyyy', # 1F6E0..1F6EC ; Common 'Zyyy', # 1F6E0..1F6EC ; Common
'Zzzz', # 1F6ED..1F6EF ; Unknown 'Zzzz', # 1F6ED..1F6EF ; Unknown
'Zyyy', # 1F6F0..1F6F9 ; Common 'Zyyy', # 1F6F0..1F6FA ; Common
'Zzzz', # 1F6FA..1F6FF ; Unknown 'Zzzz', # 1F6FB..1F6FF ; Unknown
'Zyyy', # 1F700..1F773 ; Common 'Zyyy', # 1F700..1F773 ; Common
'Zzzz', # 1F774..1F77F ; Unknown 'Zzzz', # 1F774..1F77F ; Unknown
'Zyyy', # 1F780..1F7D8 ; Common 'Zyyy', # 1F780..1F7D8 ; Common
'Zzzz', # 1F7D9..1F7FF ; Unknown 'Zzzz', # 1F7D9..1F7DF ; Unknown
'Zyyy', # 1F7E0..1F7EB ; Common
'Zzzz', # 1F7EC..1F7FF ; Unknown
'Zyyy', # 1F800..1F80B ; Common 'Zyyy', # 1F800..1F80B ; Common
'Zzzz', # 1F80C..1F80F ; Unknown 'Zzzz', # 1F80C..1F80F ; Unknown
'Zyyy', # 1F810..1F847 ; Common 'Zyyy', # 1F810..1F847 ; Common
@ -3063,25 +3105,29 @@ VALUES = [
'Zyyy', # 1F890..1F8AD ; Common 'Zyyy', # 1F890..1F8AD ; Common
'Zzzz', # 1F8AE..1F8FF ; Unknown 'Zzzz', # 1F8AE..1F8FF ; Unknown
'Zyyy', # 1F900..1F90B ; Common 'Zyyy', # 1F900..1F90B ; Common
'Zzzz', # 1F90C..1F90F ; Unknown 'Zzzz', # 1F90C..1F90C ; Unknown
'Zyyy', # 1F910..1F93E ; Common 'Zyyy', # 1F90D..1F971 ; Common
'Zzzz', # 1F93F..1F93F ; Unknown 'Zzzz', # 1F972..1F972 ; Unknown
'Zyyy', # 1F940..1F970 ; Common
'Zzzz', # 1F971..1F972 ; Unknown
'Zyyy', # 1F973..1F976 ; Common 'Zyyy', # 1F973..1F976 ; Common
'Zzzz', # 1F977..1F979 ; Unknown 'Zzzz', # 1F977..1F979 ; Unknown
'Zyyy', # 1F97A..1F97A ; Common 'Zyyy', # 1F97A..1F9A2 ; Common
'Zzzz', # 1F97B..1F97B ; Unknown 'Zzzz', # 1F9A3..1F9A4 ; Unknown
'Zyyy', # 1F97C..1F9A2 ; Common 'Zyyy', # 1F9A5..1F9AA ; Common
'Zzzz', # 1F9A3..1F9AF ; Unknown 'Zzzz', # 1F9AB..1F9AD ; Unknown
'Zyyy', # 1F9B0..1F9B9 ; Common 'Zyyy', # 1F9AE..1F9CA ; Common
'Zzzz', # 1F9BA..1F9BF ; Unknown 'Zzzz', # 1F9CB..1F9CC ; Unknown
'Zyyy', # 1F9C0..1F9C2 ; Common 'Zyyy', # 1F9CD..1FA53 ; Common
'Zzzz', # 1F9C3..1F9CF ; Unknown 'Zzzz', # 1FA54..1FA5F ; Unknown
'Zyyy', # 1F9D0..1F9FF ; Common
'Zzzz', # 1FA00..1FA5F ; Unknown
'Zyyy', # 1FA60..1FA6D ; Common 'Zyyy', # 1FA60..1FA6D ; Common
'Zzzz', # 1FA6E..1FFFF ; Unknown 'Zzzz', # 1FA6E..1FA6F ; Unknown
'Zyyy', # 1FA70..1FA73 ; Common
'Zzzz', # 1FA74..1FA77 ; Unknown
'Zyyy', # 1FA78..1FA7A ; Common
'Zzzz', # 1FA7B..1FA7F ; Unknown
'Zyyy', # 1FA80..1FA82 ; Common
'Zzzz', # 1FA83..1FA8F ; Unknown
'Zyyy', # 1FA90..1FA95 ; Common
'Zzzz', # 1FA96..1FFFF ; Unknown
'Hani', # 20000..2A6D6 ; Han 'Hani', # 20000..2A6D6 ; Han
'Zzzz', # 2A6D7..2A6FF ; Unknown 'Zzzz', # 2A6D7..2A6FF ; Unknown
'Hani', # 2A700..2B734 ; Han 'Hani', # 2A700..2B734 ; Han
@ -3135,6 +3181,7 @@ NAMES = {
'Dupl': 'Duployan', 'Dupl': 'Duployan',
'Egyp': 'Egyptian_Hieroglyphs', 'Egyp': 'Egyptian_Hieroglyphs',
'Elba': 'Elbasan', 'Elba': 'Elbasan',
'Elym': 'Elymaic',
'Ethi': 'Ethiopic', 'Ethi': 'Ethiopic',
'Geor': 'Georgian', 'Geor': 'Georgian',
'Glag': 'Glagolitic', 'Glag': 'Glagolitic',
@ -3153,6 +3200,7 @@ NAMES = {
'Hira': 'Hiragana', 'Hira': 'Hiragana',
'Hluw': 'Anatolian_Hieroglyphs', 'Hluw': 'Anatolian_Hieroglyphs',
'Hmng': 'Pahawh_Hmong', 'Hmng': 'Pahawh_Hmong',
'Hmnp': 'Nyiakeng_Puachue_Hmong',
'Hrkt': 'Katakana_Or_Hiragana', 'Hrkt': 'Katakana_Or_Hiragana',
'Hung': 'Old_Hungarian', 'Hung': 'Old_Hungarian',
'Ital': 'Old_Italic', 'Ital': 'Old_Italic',
@ -3190,6 +3238,7 @@ NAMES = {
'Mtei': 'Meetei_Mayek', 'Mtei': 'Meetei_Mayek',
'Mult': 'Multani', 'Mult': 'Multani',
'Mymr': 'Myanmar', 'Mymr': 'Myanmar',
'Nand': 'Nandinagari',
'Narb': 'Old_North_Arabian', 'Narb': 'Old_North_Arabian',
'Nbat': 'Nabataean', 'Nbat': 'Nabataean',
'Newa': 'Newa', 'Newa': 'Newa',
@ -3246,6 +3295,7 @@ NAMES = {
'Ugar': 'Ugaritic', 'Ugar': 'Ugaritic',
'Vaii': 'Vai', 'Vaii': 'Vai',
'Wara': 'Warang_Citi', 'Wara': 'Warang_Citi',
'Wcho': 'Wancho',
'Xpeo': 'Old_Persian', 'Xpeo': 'Old_Persian',
'Xsux': 'Cuneiform', 'Xsux': 'Cuneiform',
'Yiii': 'Yi', 'Yiii': 'Yi',

View File

@ -161,7 +161,7 @@ def merge_PrivateDicts(top_dicts, vsindex_dict, var_model, fd_map):
For each key, step through each relevant source font Private dict, and For each key, step through each relevant source font Private dict, and
build a list of values to blend. build a list of values to blend.
The 'relevant' source fonts are selected by first getting the right The 'relevant' source fonts are selected by first getting the right
submodel using model_keys[vsindex]. The indices of the submodel using vsindex_dict[vsindex]. The indices of the
subModel.locations are mapped to source font list indices by subModel.locations are mapped to source font list indices by
assuming the latter order is the same as the order of the assuming the latter order is the same as the order of the
var_model.locations. I can then get the index of each subModel var_model.locations. I can then get the index of each subModel
@ -180,7 +180,7 @@ def merge_PrivateDicts(top_dicts, vsindex_dict, var_model, fd_map):
# At the moment, no PrivateDict has a vsindex key, but let's support # At the moment, no PrivateDict has a vsindex key, but let's support
# how it should work. See comment at end of # how it should work. See comment at end of
# merge_charstrings() - still need to optimize use of vsindex. # merge_charstrings() - still need to optimize use of vsindex.
sub_model, model_keys = vsindex_dict[vsindex] sub_model, _ = vsindex_dict[vsindex]
master_indices = [] master_indices = []
for loc in sub_model.locations[1:]: for loc in sub_model.locations[1:]:
i = var_model.locations.index(loc) - 1 i = var_model.locations.index(loc) - 1
@ -270,7 +270,9 @@ def getfd_map(varFont, fonts_list):
num_regions = len(region_fonts) num_regions = len(region_fonts)
topDict = default_font['CFF '].cff.topDictIndex[0] topDict = default_font['CFF '].cff.topDictIndex[0]
if not hasattr(topDict, 'FDSelect'): if not hasattr(topDict, 'FDSelect'):
fd_map[0] = [0]*num_regions # All glyphs reference only one FontDict.
# Map the FD index for regions to index 0.
fd_map[0] = {ri:0 for ri in range(num_regions)}
return fd_map return fd_map
gname_mapping = {} gname_mapping = {}
@ -317,6 +319,19 @@ def _get_cs(charstrings, glyphName):
return None return None
return charstrings[glyphName] return charstrings[glyphName]
def _add_new_vsindex(model, key, masterSupports, vsindex_dict,
vsindex_by_key, varDataList):
varTupleIndexes = []
for support in model.supports[1:]:
if support not in masterSupports:
masterSupports.append(support)
varTupleIndexes.append(masterSupports.index(support))
var_data = varLib.builder.buildVarData(varTupleIndexes, None, False)
vsindex = len(vsindex_dict)
vsindex_by_key[key] = vsindex
vsindex_dict[vsindex] = (model, [key])
varDataList.append(var_data)
return vsindex
def merge_charstrings(glyphOrder, num_masters, top_dicts, masterModel): def merge_charstrings(glyphOrder, num_masters, top_dicts, masterModel):
@ -365,24 +380,24 @@ def merge_charstrings(glyphOrder, num_masters, top_dicts, masterModel):
# If the charstring required a new model, create # If the charstring required a new model, create
# a VarData table to go with, and set vsindex. # a VarData table to go with, and set vsindex.
key = tuple(v is not None for v in all_cs)
try: try:
key = tuple(v is not None for v in all_cs)
vsindex = vsindex_by_key[key] vsindex = vsindex_by_key[key]
except KeyError: except KeyError:
varTupleIndexes = [] vsindex = _add_new_vsindex(model, key, masterSupports, vsindex_dict,
for support in model.supports[1:]: vsindex_by_key, varDataList)
if support not in masterSupports:
masterSupports.append(support)
varTupleIndexes.append(masterSupports.index(support))
var_data = varLib.builder.buildVarData(varTupleIndexes, None, False)
vsindex = len(vsindex_dict)
vsindex_by_key[key] = vsindex
vsindex_dict[vsindex] = (model, [key])
varDataList.append(var_data)
# We do not need to check for an existing new_cs.private.vsindex, # We do not need to check for an existing new_cs.private.vsindex,
# as we know it doesn't exist yet. # as we know it doesn't exist yet.
if vsindex != 0: if vsindex != 0:
new_cs.program[:0] = [vsindex, 'vsindex'] new_cs.program[:0] = [vsindex, 'vsindex']
# If there is no variation in any of the charstrings, then vsindex_dict
# never gets built. This could still be needed if there is variation
# in the PrivatDict, so we will build the default data for vsindex = 0.
if not vsindex_dict:
key = (True,) * num_masters
_add_new_vsindex(model, key, masterSupports, vsindex_dict,
vsindex_by_key, varDataList)
cvData = CVarData(varDataList=varDataList, masterSupports=masterSupports, cvData = CVarData(varDataList=varDataList, masterSupports=masterSupports,
vsindex_dict=vsindex_dict) vsindex_dict=vsindex_dict)
# XXX To do: optimize use of vsindex between the PrivateDicts and # XXX To do: optimize use of vsindex between the PrivateDicts and

View File

@ -2,6 +2,8 @@
Merge OpenType Layout tables (GDEF / GPOS / GSUB). Merge OpenType Layout tables (GDEF / GPOS / GSUB).
""" """
from __future__ import print_function, division, absolute_import from __future__ import print_function, division, absolute_import
import copy
from operator import ior
from fontTools.misc.py23 import * from fontTools.misc.py23 import *
from fontTools.misc.fixedTools import otRound from fontTools.misc.fixedTools import otRound
from fontTools.misc import classifyTools from fontTools.misc import classifyTools
@ -12,6 +14,7 @@ from fontTools.varLib import builder, models, varStore
from fontTools.varLib.models import nonNone, allNone, allEqual, allEqualTo from fontTools.varLib.models import nonNone, allNone, allEqual, allEqualTo
from fontTools.varLib.varStore import VarStoreInstancer from fontTools.varLib.varStore import VarStoreInstancer
from functools import reduce from functools import reduce
from fontTools.otlLib.builder import buildSinglePos
class Merger(object): class Merger(object):
@ -456,7 +459,7 @@ def _PairPosFormat2_align_matrices(self, lst, font, transparent=False):
exemplarGlyph = next(iter(classSet)) exemplarGlyph = next(iter(classSet))
klass = classDef2.get(exemplarGlyph, 0) klass = classDef2.get(exemplarGlyph, 0)
rec2 = oldClass2Records[klass] rec2 = oldClass2Records[klass]
class2Records.append(rec2) class2Records.append(copy.deepcopy(rec2))
class1Records.append(rec1new) class1Records.append(rec1new)
new_matrices.append(class1Records) new_matrices.append(class1Records)
matrices = new_matrices matrices = new_matrices
@ -727,6 +730,30 @@ def _Lookup_PairPos_subtables_canonicalize(lst, font):
return lst return lst
def _Lookup_SinglePos_subtables_flatten(lst, font, min_inclusive_rec_format):
glyphs, _ = _merge_GlyphOrders(font,
[v.Coverage.glyphs for v in lst], None)
num_glyphs = len(glyphs)
new = ot.SinglePos()
new.Format = 2
new.ValueFormat = min_inclusive_rec_format
new.Coverage = ot.Coverage()
new.Coverage.glyphs = glyphs
new.ValueCount = num_glyphs
new.Value = [None] * num_glyphs
for singlePos in lst:
if singlePos.Format == 1:
val_rec = singlePos.Value
for gname in singlePos.Coverage.glyphs:
i = glyphs.index(gname)
new.Value[i] = copy.deepcopy(val_rec)
elif singlePos.Format == 2:
for j, gname in enumerate(singlePos.Coverage.glyphs):
val_rec = singlePos.Value[j]
i = glyphs.index(gname)
new.Value[i] = copy.deepcopy(val_rec)
return [new]
@AligningMerger.merger(ot.Lookup) @AligningMerger.merger(ot.Lookup)
def merge(merger, self, lst): def merge(merger, self, lst):
subtables = merger.lookup_subtables = [l.SubTable for l in lst] subtables = merger.lookup_subtables = [l.SubTable for l in lst]
@ -746,12 +773,28 @@ def merge(merger, self, lst):
isPairPos = self.SubTable and isinstance(self.SubTable[0], ot.PairPos) isPairPos = self.SubTable and isinstance(self.SubTable[0], ot.PairPos)
if isPairPos: if isPairPos:
# AFDKO and feaLib sometimes generate two Format1 subtables instead of one. # AFDKO and feaLib sometimes generate two Format1 subtables instead of one.
# Merge those before continuing. # Merge those before continuing.
# https://github.com/fonttools/fonttools/issues/719 # https://github.com/fonttools/fonttools/issues/719
self.SubTable = _Lookup_PairPos_subtables_canonicalize(self.SubTable, merger.font) self.SubTable = _Lookup_PairPos_subtables_canonicalize(self.SubTable, merger.font)
subtables = merger.lookup_subtables = [_Lookup_PairPos_subtables_canonicalize(st, merger.font) for st in subtables] subtables = merger.lookup_subtables = [_Lookup_PairPos_subtables_canonicalize(st, merger.font) for st in subtables]
else:
isSinglePos = self.SubTable and isinstance(self.SubTable[0], ot.SinglePos)
if isSinglePos:
numSubtables = [len(st) for st in subtables]
if not all([nums == numSubtables[0] for nums in numSubtables]):
# Flatten list of SinglePos subtables to single Format 2 subtable,
# with all value records set to the rec format type.
# We use buildSinglePos() to optimize the lookup after merging.
valueFormatList = [t.ValueFormat for st in subtables for t in st]
# Find the minimum value record that can accomodate all the singlePos subtables.
mirf = reduce(ior, valueFormatList)
self.SubTable = _Lookup_SinglePos_subtables_flatten(self.SubTable, merger.font, mirf)
subtables = merger.lookup_subtables = [
_Lookup_SinglePos_subtables_flatten(st, merger.font, mirf) for st in subtables]
flattened = True
else:
flattened = False
merger.mergeLists(self.SubTable, subtables) merger.mergeLists(self.SubTable, subtables)
self.SubTableCount = len(self.SubTable) self.SubTableCount = len(self.SubTable)
@ -769,6 +812,16 @@ def merge(merger, self, lst):
self.SubTable.pop(-1) self.SubTable.pop(-1)
self.SubTableCount -= 1 self.SubTableCount -= 1
elif isSinglePos and flattened:
singlePosTable = self.SubTable[0]
glyphs = singlePosTable.Coverage.glyphs
# We know that singlePosTable is Format 2, as this is set
# in _Lookup_SinglePos_subtables_flatten.
singlePosMapping = {
gname: valRecord
for gname, valRecord in zip(glyphs, singlePosTable.Value)
}
self.SubTable = buildSinglePos(singlePosMapping, merger.font.getReverseGlyphMap())
merger.mergeObjects(self, lst, exclude=['SubTable', 'SubTableCount']) merger.mergeObjects(self, lst, exclude=['SubTable', 'SubTableCount'])
del merger.lookup_subtables del merger.lookup_subtables

View File

@ -1,3 +1,28 @@
3.43.0 (released 2019-06-18)
----------------------------
- [woff2] Added support for compressing/decompressing WOFF2 fonts with non-transformed
``glyf`` and ``loca`` tables, as well as with transformed ``hmtx`` table.
Removed ``Snippets/woff2_compress.py`` and ``Snippets/woff2_decompress.py`` scripts,
and replaced them with a new console entry point ``fonttools ttLib.woff2``
that provides two sub-commands ``compress`` and ``decompress``.
- [varLib.cff] Fixed bug when merging CFF2 ``PrivateDicts``. The ``PrivateDict``
data from the first region font was incorrecty used for all subsequent fonts.
The bug would only affect variable CFF2 fonts with hinting (#1643, #1644).
Also, fixed a merging bug when VF masters have no blends or marking glyphs (#1632,
#1642).
- [loggingTools] Removed unused backport of ``LastResortLogger`` class.
- [subset] Gracefully handle partial MATH table (#1635).
- [featureVars] Avoid duplicate references to ``rvrn`` feature record in
``DefaultLangSys`` tables when calling ``addFeatureVariations`` on a font that
does not already have a ``GSUB`` table (aa8a5bc6).
- [varLib] Fixed merging of class-based kerning. Before, the process could introduce
rogue kerning values and variations for random classes against class zero (everything
not otherwise classed).
- [varLib] Fixed merging GPOS tables from master fonts with different number of
``SinglePos`` subtables (#1621, #1641).
- [unicodedata] Updated Blocks, Scripts and ScriptExtensions to Unicode 12.1.
3.42.0 (released 2019-05-28) 3.42.0 (released 2019-05-28)
---------------------------- ----------------------------

View File

@ -1,29 +0,0 @@
#!/usr/bin/env python
from __future__ import print_function, division, absolute_import
from fontTools.misc.py23 import *
from fontTools.ttLib import TTFont
from fontTools.ttx import makeOutputFileName
import sys
import os
def main(args=None):
if args is None:
args = sys.argv[1:]
if len(args) < 1:
print("One argument, the input filename, must be provided.", file=sys.stderr)
return 1
filename = args[0]
outfilename = makeOutputFileName(filename, outputDir=None, extension='.woff2')
print("Processing %s => %s" % (filename, outfilename))
font = TTFont(filename, recalcBBoxes=False, recalcTimestamp=False)
font.flavor = "woff2"
font.save(outfilename, reorderTables=False)
if __name__ == '__main__':
sys.exit(main())

View File

@ -1,39 +0,0 @@
#!/usr/bin/env python
from __future__ import print_function, division, absolute_import
from fontTools.misc.py23 import *
from fontTools.ttLib import TTFont
from fontTools.ttx import makeOutputFileName
import sys
import os
def make_output_name(filename):
with open(filename, "rb") as f:
f.seek(4)
sfntVersion = f.read(4)
assert len(sfntVersion) == 4, "not enough data"
ext = '.ttf' if sfntVersion == b"\x00\x01\x00\x00" else ".otf"
outfilename = makeOutputFileName(filename, outputDir=None, extension=ext)
return outfilename
def main(args=None):
if args is None:
args = sys.argv[1:]
if len(args) < 1:
print("One argument, the input filename, must be provided.", file=sys.stderr)
return 1
filename = args[0]
outfilename = make_output_name(filename)
print("Processing %s => %s" % (filename, outfilename))
font = TTFont(filename, recalcBBoxes=False, recalcTimestamp=False)
font.flavor = None
font.save(outfilename, reorderTables=True)
if __name__ == '__main__':
sys.exit(main())

View File

@ -1,19 +1,24 @@
from __future__ import print_function, division, absolute_import, unicode_literals from __future__ import print_function, division, absolute_import, unicode_literals
from fontTools.misc.py23 import * from fontTools.misc.py23 import *
from fontTools import ttLib from fontTools import ttLib
from fontTools.ttLib import woff2
from fontTools.ttLib.woff2 import ( from fontTools.ttLib.woff2 import (
WOFF2Reader, woff2DirectorySize, woff2DirectoryFormat, WOFF2Reader, woff2DirectorySize, woff2DirectoryFormat,
woff2FlagsSize, woff2UnknownTagSize, woff2Base128MaxSize, WOFF2DirectoryEntry, woff2FlagsSize, woff2UnknownTagSize, woff2Base128MaxSize, WOFF2DirectoryEntry,
getKnownTagIndex, packBase128, base128Size, woff2UnknownTagIndex, getKnownTagIndex, packBase128, base128Size, woff2UnknownTagIndex,
WOFF2FlavorData, woff2TransformedTableTags, WOFF2GlyfTable, WOFF2LocaTable, WOFF2FlavorData, woff2TransformedTableTags, WOFF2GlyfTable, WOFF2LocaTable,
WOFF2Writer, unpackBase128, unpack255UShort, pack255UShort) WOFF2HmtxTable, WOFF2Writer, unpackBase128, unpack255UShort, pack255UShort)
import unittest import unittest
from fontTools.misc import sstruct from fontTools.misc import sstruct
from fontTools import fontBuilder
from fontTools.pens.ttGlyphPen import TTGlyphPen
import struct import struct
import os import os
import random import random
import copy import copy
from collections import OrderedDict from collections import OrderedDict
from functools import partial
import pytest
haveBrotli = False haveBrotli = False
try: try:
@ -122,7 +127,7 @@ class WOFF2ReaderTest(unittest.TestCase):
def test_reconstruct_unknown(self): def test_reconstruct_unknown(self):
reader = WOFF2Reader(self.file) reader = WOFF2Reader(self.file)
with self.assertRaisesRegex(ttLib.TTLibError, 'transform for table .* unknown'): with self.assertRaisesRegex(ttLib.TTLibError, 'transform for table .* unknown'):
reader.reconstructTable('ZZZZ') reader.reconstructTable('head')
class WOFF2ReaderTTFTest(WOFF2ReaderTest): class WOFF2ReaderTTFTest(WOFF2ReaderTest):
@ -243,10 +248,6 @@ class WOFF2DirectoryEntryTest(unittest.TestCase):
with self.assertRaisesRegex(ttLib.TTLibError, "can't read table 'tag'"): with self.assertRaisesRegex(ttLib.TTLibError, "can't read table 'tag'"):
self.entry.fromString(bytes(incompleteData)) self.entry.fromString(bytes(incompleteData))
def test_table_reserved_flags(self):
with self.assertRaisesRegex(ttLib.TTLibError, "bits 6-7 are reserved"):
self.entry.fromString(bytechr(0xC0))
def test_loca_zero_transformLength(self): def test_loca_zero_transformLength(self):
data = bytechr(getKnownTagIndex('loca')) # flags data = bytechr(getKnownTagIndex('loca')) # flags
data += packBase128(random.randint(1, 100)) # origLength data += packBase128(random.randint(1, 100)) # origLength
@ -292,6 +293,35 @@ class WOFF2DirectoryEntryTest(unittest.TestCase):
data = self.entry.toString() data = self.entry.toString()
self.assertEqual(len(data), expectedSize) self.assertEqual(len(data), expectedSize)
def test_glyf_loca_transform_flags(self):
for tag in ("glyf", "loca"):
entry = WOFF2DirectoryEntry()
entry.tag = Tag(tag)
entry.flags = getKnownTagIndex(entry.tag)
self.assertEqual(entry.transformVersion, 0)
self.assertTrue(entry.transformed)
entry.transformed = False
self.assertEqual(entry.transformVersion, 3)
self.assertEqual(entry.flags & 0b11000000, (3 << 6))
self.assertFalse(entry.transformed)
def test_other_transform_flags(self):
entry = WOFF2DirectoryEntry()
entry.tag = Tag('ZZZZ')
entry.flags = woff2UnknownTagIndex
self.assertEqual(entry.transformVersion, 0)
self.assertFalse(entry.transformed)
entry.transformed = True
self.assertEqual(entry.transformVersion, 1)
self.assertEqual(entry.flags & 0b11000000, (1 << 6))
self.assertTrue(entry.transformed)
class DummyReader(WOFF2Reader): class DummyReader(WOFF2Reader):
@ -300,6 +330,7 @@ class DummyReader(WOFF2Reader):
for attr in ('majorVersion', 'minorVersion', 'metaOffset', 'metaLength', for attr in ('majorVersion', 'minorVersion', 'metaOffset', 'metaLength',
'metaOrigLength', 'privLength', 'privOffset'): 'metaOrigLength', 'privLength', 'privOffset'):
setattr(self, attr, 0) setattr(self, attr, 0)
self.tables = {}
class WOFF2FlavorDataTest(unittest.TestCase): class WOFF2FlavorDataTest(unittest.TestCase):
@ -354,6 +385,24 @@ class WOFF2FlavorDataTest(unittest.TestCase):
self.assertEqual(flavorData.majorVersion, 1) self.assertEqual(flavorData.majorVersion, 1)
self.assertEqual(flavorData.minorVersion, 1) self.assertEqual(flavorData.minorVersion, 1)
def test_mutually_exclusive_args(self):
reader = DummyReader(self.file)
with self.assertRaisesRegex(TypeError, "arguments are mutually exclusive"):
WOFF2FlavorData(reader, transformedTables={"hmtx"})
def test_transformTables_default(self):
flavorData = WOFF2FlavorData()
self.assertEqual(flavorData.transformedTables, set(woff2TransformedTableTags))
def test_transformTables_invalid(self):
msg = r"'glyf' and 'loca' must be transformed \(or not\) together"
with self.assertRaisesRegex(ValueError, msg):
WOFF2FlavorData(transformedTables={"glyf"})
with self.assertRaisesRegex(ValueError, msg):
WOFF2FlavorData(transformedTables={"loca"})
class WOFF2WriterTest(unittest.TestCase): class WOFF2WriterTest(unittest.TestCase):
@ -512,6 +561,30 @@ class WOFF2WriterTest(unittest.TestCase):
flavorData.majorVersion, flavorData.minorVersion = (10, 11) flavorData.majorVersion, flavorData.minorVersion = (10, 11)
self.assertEqual((10, 11), self.writer._getVersion()) self.assertEqual((10, 11), self.writer._getVersion())
def test_hmtx_trasform(self):
tableTransforms = {"glyf", "loca", "hmtx"}
writer = WOFF2Writer(BytesIO(), self.numTables, self.font.sfntVersion)
writer.flavorData = WOFF2FlavorData(transformedTables=tableTransforms)
for tag in self.tags:
writer[tag] = self.font.getTableData(tag)
writer.close()
# enabling hmtx transform has no effect when font has no glyf table
self.assertEqual(writer.file.getvalue(), CFF_WOFF2.getvalue())
def test_no_transforms(self):
writer = WOFF2Writer(BytesIO(), self.numTables, self.font.sfntVersion)
writer.flavorData = WOFF2FlavorData(transformedTables=())
for tag in self.tags:
writer[tag] = self.font.getTableData(tag)
writer.close()
# transforms settings have no effect when font is CFF-flavored, since
# all the current transforms only apply to TrueType-flavored fonts.
self.assertEqual(writer.file.getvalue(), CFF_WOFF2.getvalue())
class WOFF2WriterTTFTest(WOFF2WriterTest): class WOFF2WriterTTFTest(WOFF2WriterTest):
@ -540,6 +613,35 @@ class WOFF2WriterTTFTest(WOFF2WriterTest):
for tag in normTables: for tag in normTables:
self.assertEqual(self.writer.tables[tag].data, normTables[tag]) self.assertEqual(self.writer.tables[tag].data, normTables[tag])
def test_hmtx_trasform(self):
tableTransforms = {"glyf", "loca", "hmtx"}
writer = WOFF2Writer(BytesIO(), self.numTables, self.font.sfntVersion)
writer.flavorData = WOFF2FlavorData(transformedTables=tableTransforms)
for tag in self.tags:
writer[tag] = self.font.getTableData(tag)
writer.close()
length = len(writer.file.getvalue())
# enabling optional hmtx transform shaves off a few bytes
self.assertLess(length, len(TT_WOFF2.getvalue()))
def test_no_transforms(self):
writer = WOFF2Writer(BytesIO(), self.numTables, self.font.sfntVersion)
writer.flavorData = WOFF2FlavorData(transformedTables=())
for tag in self.tags:
writer[tag] = self.font.getTableData(tag)
writer.close()
self.assertNotEqual(writer.file.getvalue(), TT_WOFF2.getvalue())
writer.file.seek(0)
reader = WOFF2Reader(writer.file)
self.assertEqual(len(reader.flavorData.transformedTables), 0)
class WOFF2LocaTableTest(unittest.TestCase): class WOFF2LocaTableTest(unittest.TestCase):
@ -709,28 +811,6 @@ class WOFF2GlyfTableTest(unittest.TestCase):
data = glyfTable.transform(self.font) data = glyfTable.transform(self.font)
self.assertEqual(self.transformedGlyfData, data) self.assertEqual(self.transformedGlyfData, data)
def test_transform_glyf_incorrect_glyphOrder(self):
glyfTable = self.font['glyf']
badGlyphOrder = self.font.getGlyphOrder()[:-1]
del glyfTable.glyphOrder
self.font.setGlyphOrder(badGlyphOrder)
with self.assertRaisesRegex(ttLib.TTLibError, "incorrect glyphOrder"):
glyfTable.transform(self.font)
glyfTable.glyphOrder = badGlyphOrder
with self.assertRaisesRegex(ttLib.TTLibError, "incorrect glyphOrder"):
glyfTable.transform(self.font)
def test_transform_glyf_missing_glyphOrder(self):
glyfTable = self.font['glyf']
del glyfTable.glyphOrder
del self.font.glyphOrder
numGlyphs = self.font['maxp'].numGlyphs
del self.font['maxp']
glyfTable.transform(self.font)
expected = [".notdef"]
expected.extend(["glyph%.5d" % i for i in range(1, numGlyphs)])
self.assertEqual(expected, glyfTable.glyphOrder)
def test_roundtrip_glyf_reconstruct_and_transform(self): def test_roundtrip_glyf_reconstruct_and_transform(self):
glyfTable = WOFF2GlyfTable() glyfTable = WOFF2GlyfTable()
glyfTable.reconstruct(self.transformedGlyfData, self.font) glyfTable.reconstruct(self.transformedGlyfData, self.font)
@ -748,6 +828,471 @@ class WOFF2GlyfTableTest(unittest.TestCase):
self.assertEqual(normGlyfData, reconstructedData) self.assertEqual(normGlyfData, reconstructedData)
@pytest.fixture(scope="module")
def fontfile():
class Glyph(object):
def __init__(self, empty=False, **kwargs):
if not empty:
self.draw = partial(self.drawRect, **kwargs)
else:
self.draw = lambda pen: None
@staticmethod
def drawRect(pen, xMin, xMax):
pen.moveTo((xMin, 0))
pen.lineTo((xMin, 1000))
pen.lineTo((xMax, 1000))
pen.lineTo((xMax, 0))
pen.closePath()
class CompositeGlyph(object):
def __init__(self, components):
self.components = components
def draw(self, pen):
for baseGlyph, (offsetX, offsetY) in self.components:
pen.addComponent(baseGlyph, (1, 0, 0, 1, offsetX, offsetY))
fb = fontBuilder.FontBuilder(unitsPerEm=1000, isTTF=True)
fb.setupGlyphOrder(
[".notdef", "space", "A", "acutecomb", "Aacute", "zero", "one", "two"]
)
fb.setupCharacterMap(
{
0x20: "space",
0x41: "A",
0x0301: "acutecomb",
0xC1: "Aacute",
0x30: "zero",
0x31: "one",
0x32: "two",
}
)
fb.setupHorizontalMetrics(
{
".notdef": (500, 50),
"space": (600, 0),
"A": (550, 40),
"acutecomb": (0, -40),
"Aacute": (550, 40),
"zero": (500, 30),
"one": (500, 50),
"two": (500, 40),
}
)
fb.setupHorizontalHeader(ascent=1000, descent=-200)
srcGlyphs = {
".notdef": Glyph(xMin=50, xMax=450),
"space": Glyph(empty=True),
"A": Glyph(xMin=40, xMax=510),
"acutecomb": Glyph(xMin=-40, xMax=60),
"Aacute": CompositeGlyph([("A", (0, 0)), ("acutecomb", (200, 0))]),
"zero": Glyph(xMin=30, xMax=470),
"one": Glyph(xMin=50, xMax=450),
"two": Glyph(xMin=40, xMax=460),
}
pen = TTGlyphPen(srcGlyphs)
glyphSet = {}
for glyphName, glyph in srcGlyphs.items():
glyph.draw(pen)
glyphSet[glyphName] = pen.glyph()
fb.setupGlyf(glyphSet)
fb.setupNameTable(
{
"familyName": "TestWOFF2",
"styleName": "Regular",
"uniqueFontIdentifier": "TestWOFF2 Regular; Version 1.000; ABCD",
"fullName": "TestWOFF2 Regular",
"version": "Version 1.000",
"psName": "TestWOFF2-Regular",
}
)
fb.setupOS2()
fb.setupPost()
buf = BytesIO()
fb.save(buf)
buf.seek(0)
assert fb.font["maxp"].numGlyphs == 8
assert fb.font["hhea"].numberOfHMetrics == 6
for glyphName in fb.font.getGlyphOrder():
xMin = getattr(fb.font["glyf"][glyphName], "xMin", 0)
assert xMin == fb.font["hmtx"][glyphName][1]
return buf
@pytest.fixture
def ttFont(fontfile):
return ttLib.TTFont(fontfile, recalcBBoxes=False, recalcTimestamp=False)
class WOFF2HmtxTableTest(object):
def test_transform_no_sidebearings(self, ttFont):
hmtxTable = WOFF2HmtxTable()
hmtxTable.metrics = ttFont["hmtx"].metrics
data = hmtxTable.transform(ttFont)
assert data == (
b"\x03" # 00000011 | bits 0 and 1 are set (no sidebearings arrays)
# advanceWidthArray
b'\x01\xf4' # .notdef: 500
b'\x02X' # space: 600
b'\x02&' # A: 550
b'\x00\x00' # acutecomb: 0
b'\x02&' # Aacute: 550
b'\x01\xf4' # zero: 500
)
def test_transform_proportional_sidebearings(self, ttFont):
hmtxTable = WOFF2HmtxTable()
metrics = ttFont["hmtx"].metrics
# force one of the proportional glyphs to have its left sidebearing be
# different from its xMin (40)
metrics["A"] = (550, 39)
hmtxTable.metrics = metrics
assert ttFont["glyf"]["A"].xMin != metrics["A"][1]
data = hmtxTable.transform(ttFont)
assert data == (
b"\x02" # 00000010 | bits 0 unset: explicit proportional sidebearings
# advanceWidthArray
b'\x01\xf4' # .notdef: 500
b'\x02X' # space: 600
b'\x02&' # A: 550
b'\x00\x00' # acutecomb: 0
b'\x02&' # Aacute: 550
b'\x01\xf4' # zero: 500
# lsbArray
b'\x002' # .notdef: 50
b'\x00\x00' # space: 0
b"\x00'" # A: 39 (xMin: 40)
b'\xff\xd8' # acutecomb: -40
b'\x00(' # Aacute: 40
b'\x00\x1e' # zero: 30
)
def test_transform_monospaced_sidebearings(self, ttFont):
hmtxTable = WOFF2HmtxTable()
metrics = ttFont["hmtx"].metrics
hmtxTable.metrics = metrics
# force one of the monospaced glyphs at the end of hmtx table to have
# its xMin different from its left sidebearing (50)
ttFont["glyf"]["one"].xMin = metrics["one"][1] + 1
data = hmtxTable.transform(ttFont)
assert data == (
b"\x01" # 00000001 | bits 1 unset: explicit monospaced sidebearings
# advanceWidthArray
b'\x01\xf4' # .notdef: 500
b'\x02X' # space: 600
b'\x02&' # A: 550
b'\x00\x00' # acutecomb: 0
b'\x02&' # Aacute: 550
b'\x01\xf4' # zero: 500
# leftSideBearingArray
b'\x002' # one: 50 (xMin: 51)
b'\x00(' # two: 40
)
def test_transform_not_applicable(self, ttFont):
hmtxTable = WOFF2HmtxTable()
metrics = ttFont["hmtx"].metrics
# force both a proportional and monospaced glyph to have sidebearings
# different from the respective xMin coordinates
metrics["A"] = (550, 39)
metrics["one"] = (500, 51)
hmtxTable.metrics = metrics
# 'None' signals to fall back using untransformed hmtx table data
assert hmtxTable.transform(ttFont) is None
def test_reconstruct_no_sidebearings(self, ttFont):
hmtxTable = WOFF2HmtxTable()
data = (
b"\x03" # 00000011 | bits 0 and 1 are set (no sidebearings arrays)
# advanceWidthArray
b'\x01\xf4' # .notdef: 500
b'\x02X' # space: 600
b'\x02&' # A: 550
b'\x00\x00' # acutecomb: 0
b'\x02&' # Aacute: 550
b'\x01\xf4' # zero: 500
)
hmtxTable.reconstruct(data, ttFont)
assert hmtxTable.metrics == {
".notdef": (500, 50),
"space": (600, 0),
"A": (550, 40),
"acutecomb": (0, -40),
"Aacute": (550, 40),
"zero": (500, 30),
"one": (500, 50),
"two": (500, 40),
}
def test_reconstruct_proportional_sidebearings(self, ttFont):
hmtxTable = WOFF2HmtxTable()
data = (
b"\x02" # 00000010 | bits 0 unset: explicit proportional sidebearings
# advanceWidthArray
b'\x01\xf4' # .notdef: 500
b'\x02X' # space: 600
b'\x02&' # A: 550
b'\x00\x00' # acutecomb: 0
b'\x02&' # Aacute: 550
b'\x01\xf4' # zero: 500
# lsbArray
b'\x002' # .notdef: 50
b'\x00\x00' # space: 0
b"\x00'" # A: 39 (xMin: 40)
b'\xff\xd8' # acutecomb: -40
b'\x00(' # Aacute: 40
b'\x00\x1e' # zero: 30
)
hmtxTable.reconstruct(data, ttFont)
assert hmtxTable.metrics == {
".notdef": (500, 50),
"space": (600, 0),
"A": (550, 39),
"acutecomb": (0, -40),
"Aacute": (550, 40),
"zero": (500, 30),
"one": (500, 50),
"two": (500, 40),
}
assert ttFont["glyf"]["A"].xMin == 40
def test_reconstruct_monospaced_sidebearings(self, ttFont):
hmtxTable = WOFF2HmtxTable()
data = (
b"\x01" # 00000001 | bits 1 unset: explicit monospaced sidebearings
# advanceWidthArray
b'\x01\xf4' # .notdef: 500
b'\x02X' # space: 600
b'\x02&' # A: 550
b'\x00\x00' # acutecomb: 0
b'\x02&' # Aacute: 550
b'\x01\xf4' # zero: 500
# leftSideBearingArray
b'\x003' # one: 51 (xMin: 50)
b'\x00(' # two: 40
)
hmtxTable.reconstruct(data, ttFont)
assert hmtxTable.metrics == {
".notdef": (500, 50),
"space": (600, 0),
"A": (550, 40),
"acutecomb": (0, -40),
"Aacute": (550, 40),
"zero": (500, 30),
"one": (500, 51),
"two": (500, 40),
}
assert ttFont["glyf"]["one"].xMin == 50
def test_reconstruct_flags_reserved_bits(self):
hmtxTable = WOFF2HmtxTable()
with pytest.raises(
ttLib.TTLibError, match="Bits 2-7 of 'hmtx' flags are reserved"
):
hmtxTable.reconstruct(b"\xFF", ttFont=None)
def test_reconstruct_flags_required_bits(self):
hmtxTable = WOFF2HmtxTable()
with pytest.raises(ttLib.TTLibError, match="either bits 0 or 1 .* must set"):
hmtxTable.reconstruct(b"\x00", ttFont=None)
def test_reconstruct_too_much_data(self, ttFont):
ttFont["hhea"].numberOfHMetrics = 2
data = b'\x03\x01\xf4\x02X\x02&'
hmtxTable = WOFF2HmtxTable()
with pytest.raises(ttLib.TTLibError, match="too much 'hmtx' table data"):
hmtxTable.reconstruct(data, ttFont)
class WOFF2RoundtripTest(object):
@staticmethod
def roundtrip(infile):
infile.seek(0)
ttFont = ttLib.TTFont(infile, recalcBBoxes=False, recalcTimestamp=False)
outfile = BytesIO()
ttFont.save(outfile)
return outfile, ttFont
def test_roundtrip_default_transforms(self, ttFont):
ttFont.flavor = "woff2"
# ttFont.flavorData = None
tmp = BytesIO()
ttFont.save(tmp)
tmp2, ttFont2 = self.roundtrip(tmp)
assert tmp.getvalue() == tmp2.getvalue()
assert ttFont2.reader.flavorData.transformedTables == {"glyf", "loca"}
def test_roundtrip_no_transforms(self, ttFont):
ttFont.flavor = "woff2"
ttFont.flavorData = WOFF2FlavorData(transformedTables=[])
tmp = BytesIO()
ttFont.save(tmp)
tmp2, ttFont2 = self.roundtrip(tmp)
assert tmp.getvalue() == tmp2.getvalue()
assert not ttFont2.reader.flavorData.transformedTables
def test_roundtrip_all_transforms(self, ttFont):
ttFont.flavor = "woff2"
ttFont.flavorData = WOFF2FlavorData(transformedTables=["glyf", "loca", "hmtx"])
tmp = BytesIO()
ttFont.save(tmp)
tmp2, ttFont2 = self.roundtrip(tmp)
assert tmp.getvalue() == tmp2.getvalue()
assert ttFont2.reader.flavorData.transformedTables == {"glyf", "loca", "hmtx"}
def test_roundtrip_only_hmtx_no_glyf_transform(self, ttFont):
ttFont.flavor = "woff2"
ttFont.flavorData = WOFF2FlavorData(transformedTables=["hmtx"])
tmp = BytesIO()
ttFont.save(tmp)
tmp2, ttFont2 = self.roundtrip(tmp)
assert tmp.getvalue() == tmp2.getvalue()
assert ttFont2.reader.flavorData.transformedTables == {"hmtx"}
class MainTest(object):
@staticmethod
def make_ttf(tmpdir):
ttFont = ttLib.TTFont(recalcBBoxes=False, recalcTimestamp=False)
ttFont.importXML(TTX)
filename = str(tmpdir / "TestTTF-Regular.ttf")
ttFont.save(filename)
return filename
def test_compress_ttf(self, tmpdir):
input_file = self.make_ttf(tmpdir)
assert woff2.main(["compress", input_file]) is None
assert (tmpdir / "TestTTF-Regular.woff2").check(file=True)
def test_compress_ttf_no_glyf_transform(self, tmpdir):
input_file = self.make_ttf(tmpdir)
assert woff2.main(["compress", "--no-glyf-transform", input_file]) is None
assert (tmpdir / "TestTTF-Regular.woff2").check(file=True)
def test_compress_ttf_hmtx_transform(self, tmpdir):
input_file = self.make_ttf(tmpdir)
assert woff2.main(["compress", "--hmtx-transform", input_file]) is None
assert (tmpdir / "TestTTF-Regular.woff2").check(file=True)
def test_compress_ttf_no_glyf_transform_hmtx_transform(self, tmpdir):
input_file = self.make_ttf(tmpdir)
assert woff2.main(
["compress", "--no-glyf-transform", "--hmtx-transform", input_file]
) is None
assert (tmpdir / "TestTTF-Regular.woff2").check(file=True)
def test_compress_output_file(self, tmpdir):
input_file = self.make_ttf(tmpdir)
output_file = tmpdir / "TestTTF.woff2"
assert woff2.main(
["compress", "-o", str(output_file), str(input_file)]
) is None
assert output_file.check(file=True)
def test_compress_otf(self, tmpdir):
ttFont = ttLib.TTFont(recalcBBoxes=False, recalcTimestamp=False)
ttFont.importXML(OTX)
input_file = str(tmpdir / "TestOTF-Regular.otf")
ttFont.save(input_file)
assert woff2.main(["compress", input_file]) is None
assert (tmpdir / "TestOTF-Regular.woff2").check(file=True)
def test_decompress_ttf(self, tmpdir):
input_file = tmpdir / "TestTTF-Regular.woff2"
input_file.write_binary(TT_WOFF2.getvalue())
assert woff2.main(["decompress", str(input_file)]) is None
assert (tmpdir / "TestTTF-Regular.ttf").check(file=True)
def test_decompress_otf(self, tmpdir):
input_file = tmpdir / "TestTTF-Regular.woff2"
input_file.write_binary(CFF_WOFF2.getvalue())
assert woff2.main(["decompress", str(input_file)]) is None
assert (tmpdir / "TestTTF-Regular.otf").check(file=True)
def test_decompress_output_file(self, tmpdir):
input_file = tmpdir / "TestTTF-Regular.woff2"
input_file.write_binary(TT_WOFF2.getvalue())
output_file = tmpdir / "TestTTF.ttf"
assert woff2.main(
["decompress", "-o", str(output_file), str(input_file)]
) is None
assert output_file.check(file=True)
def test_no_subcommand_show_help(self, capsys):
with pytest.raises(SystemExit):
woff2.main(["--help"])
captured = capsys.readouterr()
assert "usage: fonttools ttLib.woff2" in captured.out
class Base128Test(unittest.TestCase): class Base128Test(unittest.TestCase):
def test_unpackBase128(self): def test_unpackBase128(self):

View File

@ -165,8 +165,8 @@ def test_script_extension():
assert unicodedata.script_extension("\u0660") == {'Arab', 'Thaa'} assert unicodedata.script_extension("\u0660") == {'Arab', 'Thaa'}
assert unicodedata.script_extension("\u0964") == { assert unicodedata.script_extension("\u0964") == {
'Beng', 'Deva', 'Dogr', 'Gong', 'Gran', 'Gujr', 'Guru', 'Knda', 'Beng', 'Deva', 'Dogr', 'Gong', 'Gonm', 'Gran', 'Gujr', 'Guru', 'Knda',
'Mahj', 'Mlym', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml', 'Mahj', 'Mlym', 'Nand', 'Orya', 'Sind', 'Sinh', 'Sylo', 'Takr', 'Taml',
'Telu', 'Tirh'} 'Telu', 'Tirh'}

View File

@ -0,0 +1,23 @@
<?xml version='1.0' encoding='UTF-8'?>
<designspace format="4.0">
<axes>
<axis tag="wght" name="Weight" minimum="100" maximum="900" default="400"/>
</axes>
<sources>
<source filename="master_kerning_merging/0.ttf">
<location>
<dimension name="Weight" xvalue="100"/>
</location>
</source>
<source filename="master_kerning_merging/1.ttf">
<location>
<dimension name="Weight" xvalue="400"/>
</location>
</source>
<source filename="master_kerning_merging/2.ttf">
<location>
<dimension name="Weight" xvalue="900"/>
</location>
</source>
</sources>
</designspace>

View File

@ -0,0 +1,35 @@
<?xml version="1.0" encoding="utf-8"?>
<designspace format="3">
<axes>
<axis default="0.0" maximum="1000.0" minimum="0.0" name="weight" tag="wght" />
</axes>
<sources>
<source filename="master_non_marking_cff2/TestNonMarkingCFF2_ExtraLight.ufo" name="master_0">
<lib copy="1" />
<location>
<dimension name="weight" xvalue="0" />
</location>
</source>
<source filename="master_non_marking_cff2/TestNonMarkingCFF2_Regular.ufo" name="master_1">
<location>
<dimension name="weight" xvalue="1000" />
</location>
</source>
</sources>
<instances>
<instance familyname="Test Non Marking CFF2 Roman" postscriptfontname="TestNonMarkingCFF2-ExtraLight" stylename="ExtraLight">
<location>
<dimension name="weight" xvalue="0" />
</location>
<kerning />
<info />
</instance>
<instance familyname="Test Non Marking CFF2 Roman" postscriptfontname="TestNonMarkingCFF2-Regular" stylename="Regular">
<location>
<dimension name="weight" xvalue="1000" />
</location>
<kerning />
<info />
</instance>
</instances>
</designspace>

View File

@ -0,0 +1,304 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="\x00\x01\x00\x00" ttLibVersion="3.41">
<GlyphOrder>
<!-- The 'id' attribute is only for humans; it is ignored when parsed. -->
<GlyphID id="0" name=".notdef"/>
<GlyphID id="1" name="A"/>
<GlyphID id="2" name="B"/>
<GlyphID id="3" name="C"/>
<GlyphID id="4" name="D"/>
</GlyphOrder>
<head>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="1.0"/>
<fontRevision value="0.0"/>
<checkSumAdjustment value="0x341296b2"/>
<magicNumber value="0x5f0f3cf5"/>
<flags value="00000000 00000011"/>
<unitsPerEm value="1000"/>
<created value="Wed Jun 12 15:33:01 2019"/>
<modified value="Wed Jun 12 15:33:01 2019"/>
<xMin value="50"/>
<yMin value="-200"/>
<xMax value="450"/>
<yMax value="800"/>
<macStyle value="00000000 00000000"/>
<lowestRecPPEM value="6"/>
<fontDirectionHint value="2"/>
<indexToLocFormat value="0"/>
<glyphDataFormat value="0"/>
</head>
<hhea>
<tableVersion value="0x00010000"/>
<ascent value="1000"/>
<descent value="-200"/>
<lineGap value="0"/>
<advanceWidthMax value="500"/>
<minLeftSideBearing value="50"/>
<minRightSideBearing value="50"/>
<xMaxExtent value="450"/>
<caretSlopeRise value="1"/>
<caretSlopeRun value="0"/>
<caretOffset value="0"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="1"/>
</hhea>
<maxp>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="0x10000"/>
<numGlyphs value="5"/>
<maxPoints value="8"/>
<maxContours value="2"/>
<maxCompositePoints value="0"/>
<maxCompositeContours value="0"/>
<maxZones value="1"/>
<maxTwilightPoints value="0"/>
<maxStorage value="0"/>
<maxFunctionDefs value="0"/>
<maxInstructionDefs value="0"/>
<maxStackElements value="0"/>
<maxSizeOfInstructions value="0"/>
<maxComponentElements value="0"/>
<maxComponentDepth value="0"/>
</maxp>
<OS_2>
<!-- The fields 'usFirstCharIndex' and 'usLastCharIndex'
will be recalculated by the compiler -->
<version value="4"/>
<xAvgCharWidth value="500"/>
<usWeightClass value="400"/>
<usWidthClass value="5"/>
<fsType value="00000000 00000100"/>
<ySubscriptXSize value="650"/>
<ySubscriptYSize value="600"/>
<ySubscriptXOffset value="0"/>
<ySubscriptYOffset value="75"/>
<ySuperscriptXSize value="650"/>
<ySuperscriptYSize value="600"/>
<ySuperscriptXOffset value="0"/>
<ySuperscriptYOffset value="350"/>
<yStrikeoutSize value="50"/>
<yStrikeoutPosition value="300"/>
<sFamilyClass value="0"/>
<panose>
<bFamilyType value="0"/>
<bSerifStyle value="0"/>
<bWeight value="0"/>
<bProportion value="0"/>
<bContrast value="0"/>
<bStrokeVariation value="0"/>
<bArmStyle value="0"/>
<bLetterForm value="0"/>
<bMidline value="0"/>
<bXHeight value="0"/>
</panose>
<ulUnicodeRange1 value="00000000 00000000 00000000 00000001"/>
<ulUnicodeRange2 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange3 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/>
<achVendID value="NONE"/>
<fsSelection value="00000000 01000000"/>
<usFirstCharIndex value="65"/>
<usLastCharIndex value="68"/>
<sTypoAscender value="800"/>
<sTypoDescender value="-200"/>
<sTypoLineGap value="200"/>
<usWinAscent value="1000"/>
<usWinDescent value="200"/>
<ulCodePageRange1 value="00000000 00000000 00000000 00000001"/>
<ulCodePageRange2 value="00000000 00000000 00000000 00000000"/>
<sxHeight value="500"/>
<sCapHeight value="700"/>
<usDefaultChar value="0"/>
<usBreakChar value="32"/>
<usMaxContext value="2"/>
</OS_2>
<hmtx>
<mtx name=".notdef" width="500" lsb="50"/>
<mtx name="A" width="500" lsb="0"/>
<mtx name="B" width="500" lsb="0"/>
<mtx name="C" width="500" lsb="0"/>
<mtx name="D" width="500" lsb="0"/>
</hmtx>
<cmap>
<tableVersion version="0"/>
<cmap_format_4 platformID="0" platEncID="3" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
<map code="0x42" name="B"/><!-- LATIN CAPITAL LETTER B -->
<map code="0x43" name="C"/><!-- LATIN CAPITAL LETTER C -->
<map code="0x44" name="D"/><!-- LATIN CAPITAL LETTER D -->
</cmap_format_4>
<cmap_format_4 platformID="3" platEncID="1" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
<map code="0x42" name="B"/><!-- LATIN CAPITAL LETTER B -->
<map code="0x43" name="C"/><!-- LATIN CAPITAL LETTER C -->
<map code="0x44" name="D"/><!-- LATIN CAPITAL LETTER D -->
</cmap_format_4>
</cmap>
<loca>
<!-- The 'loca' table will be calculated by the compiler -->
</loca>
<glyf>
<!-- The xMin, yMin, xMax and yMax values
will be recalculated by the compiler. -->
<TTGlyph name=".notdef" xMin="50" yMin="-200" xMax="450" yMax="800">
<contour>
<pt x="50" y="-200" on="1"/>
<pt x="450" y="-200" on="1"/>
<pt x="450" y="800" on="1"/>
<pt x="50" y="800" on="1"/>
</contour>
<contour>
<pt x="100" y="-150" on="1"/>
<pt x="100" y="750" on="1"/>
<pt x="400" y="750" on="1"/>
<pt x="400" y="-150" on="1"/>
</contour>
<instructions/>
</TTGlyph>
<TTGlyph name="A"/><!-- contains no outline data -->
<TTGlyph name="B"/><!-- contains no outline data -->
<TTGlyph name="C"/><!-- contains no outline data -->
<TTGlyph name="D"/><!-- contains no outline data -->
</glyf>
<name>
<namerecord nameID="1" platformID="3" platEncID="1" langID="0x409">
Test Thin
</namerecord>
<namerecord nameID="2" platformID="3" platEncID="1" langID="0x409">
Regular
</namerecord>
<namerecord nameID="3" platformID="3" platEncID="1" langID="0x409">
0.000;NONE;Test-Thin
</namerecord>
<namerecord nameID="4" platformID="3" platEncID="1" langID="0x409">
Test Thin
</namerecord>
<namerecord nameID="5" platformID="3" platEncID="1" langID="0x409">
Version 0.000
</namerecord>
<namerecord nameID="6" platformID="3" platEncID="1" langID="0x409">
Test-Thin
</namerecord>
<namerecord nameID="16" platformID="3" platEncID="1" langID="0x409">
Test
</namerecord>
<namerecord nameID="17" platformID="3" platEncID="1" langID="0x409">
Thin
</namerecord>
</name>
<post>
<formatType value="2.0"/>
<italicAngle value="0.0"/>
<underlinePosition value="-150"/>
<underlineThickness value="50"/>
<isFixedPitch value="0"/>
<minMemType42 value="0"/>
<maxMemType42 value="0"/>
<minMemType1 value="0"/>
<maxMemType1 value="0"/>
<psNames>
<!-- This file uses unique glyph names based on the information
found in the 'post' table. Since these names might not be unique,
we have to invent artificial names in case of clashes. In order to
be able to retain the original information, we need a name to
ps name mapping for those cases where they differ. That's what
you see below.
-->
</psNames>
<extraNames>
<!-- following are the name that are not taken from the standard Mac glyph order -->
</extraNames>
</post>
<GPOS>
<Version value="0x00010000"/>
<ScriptList>
<!-- ScriptCount=1 -->
<ScriptRecord index="0">
<ScriptTag value="DFLT"/>
<Script>
<DefaultLangSys>
<ReqFeatureIndex value="65535"/>
<!-- FeatureCount=1 -->
<FeatureIndex index="0" value="0"/>
</DefaultLangSys>
<!-- LangSysCount=0 -->
</Script>
</ScriptRecord>
</ScriptList>
<FeatureList>
<!-- FeatureCount=1 -->
<FeatureRecord index="0">
<FeatureTag value="kern"/>
<Feature>
<!-- LookupCount=1 -->
<LookupListIndex index="0" value="0"/>
</Feature>
</FeatureRecord>
</FeatureList>
<LookupList>
<!-- LookupCount=1 -->
<Lookup index="0">
<LookupType value="2"/>
<LookupFlag value="8"/>
<!-- SubTableCount=1 -->
<PairPos index="0" Format="2">
<Coverage Format="1">
<Glyph value="A"/>
<Glyph value="B"/>
</Coverage>
<ValueFormat1 value="4"/>
<ValueFormat2 value="0"/>
<ClassDef1 Format="1">
<ClassDef glyph="A" class="1"/>
</ClassDef1>
<ClassDef2 Format="1">
<ClassDef glyph="C" class="1"/>
</ClassDef2>
<!-- Class1Count=2 -->
<!-- Class2Count=2 -->
<Class1Record index="0">
<Class2Record index="0">
<Value1 XAdvance="0"/>
</Class2Record>
<Class2Record index="1">
<Value1 XAdvance="10"/>
</Class2Record>
</Class1Record>
<Class1Record index="1">
<Class2Record index="0">
<Value1 XAdvance="0"/>
</Class2Record>
<Class2Record index="1">
<Value1 XAdvance="10"/>
</Class2Record>
</Class1Record>
</PairPos>
</Lookup>
</LookupList>
</GPOS>
</ttFont>

View File

@ -0,0 +1,292 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="\x00\x01\x00\x00" ttLibVersion="3.41">
<GlyphOrder>
<!-- The 'id' attribute is only for humans; it is ignored when parsed. -->
<GlyphID id="0" name=".notdef"/>
<GlyphID id="1" name="A"/>
<GlyphID id="2" name="B"/>
<GlyphID id="3" name="C"/>
<GlyphID id="4" name="D"/>
</GlyphOrder>
<head>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="1.0"/>
<fontRevision value="0.0"/>
<checkSumAdjustment value="0x340ca516"/>
<magicNumber value="0x5f0f3cf5"/>
<flags value="00000000 00000011"/>
<unitsPerEm value="1000"/>
<created value="Wed Jun 12 15:33:01 2019"/>
<modified value="Wed Jun 12 15:33:01 2019"/>
<xMin value="50"/>
<yMin value="-200"/>
<xMax value="450"/>
<yMax value="800"/>
<macStyle value="00000000 00000000"/>
<lowestRecPPEM value="6"/>
<fontDirectionHint value="2"/>
<indexToLocFormat value="0"/>
<glyphDataFormat value="0"/>
</head>
<hhea>
<tableVersion value="0x00010000"/>
<ascent value="1000"/>
<descent value="-200"/>
<lineGap value="0"/>
<advanceWidthMax value="500"/>
<minLeftSideBearing value="50"/>
<minRightSideBearing value="50"/>
<xMaxExtent value="450"/>
<caretSlopeRise value="1"/>
<caretSlopeRun value="0"/>
<caretOffset value="0"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="1"/>
</hhea>
<maxp>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="0x10000"/>
<numGlyphs value="5"/>
<maxPoints value="8"/>
<maxContours value="2"/>
<maxCompositePoints value="0"/>
<maxCompositeContours value="0"/>
<maxZones value="1"/>
<maxTwilightPoints value="0"/>
<maxStorage value="0"/>
<maxFunctionDefs value="0"/>
<maxInstructionDefs value="0"/>
<maxStackElements value="0"/>
<maxSizeOfInstructions value="0"/>
<maxComponentElements value="0"/>
<maxComponentDepth value="0"/>
</maxp>
<OS_2>
<!-- The fields 'usFirstCharIndex' and 'usLastCharIndex'
will be recalculated by the compiler -->
<version value="4"/>
<xAvgCharWidth value="500"/>
<usWeightClass value="400"/>
<usWidthClass value="5"/>
<fsType value="00000000 00000100"/>
<ySubscriptXSize value="650"/>
<ySubscriptYSize value="600"/>
<ySubscriptXOffset value="0"/>
<ySubscriptYOffset value="75"/>
<ySuperscriptXSize value="650"/>
<ySuperscriptYSize value="600"/>
<ySuperscriptXOffset value="0"/>
<ySuperscriptYOffset value="350"/>
<yStrikeoutSize value="50"/>
<yStrikeoutPosition value="300"/>
<sFamilyClass value="0"/>
<panose>
<bFamilyType value="0"/>
<bSerifStyle value="0"/>
<bWeight value="0"/>
<bProportion value="0"/>
<bContrast value="0"/>
<bStrokeVariation value="0"/>
<bArmStyle value="0"/>
<bLetterForm value="0"/>
<bMidline value="0"/>
<bXHeight value="0"/>
</panose>
<ulUnicodeRange1 value="00000000 00000000 00000000 00000001"/>
<ulUnicodeRange2 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange3 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/>
<achVendID value="NONE"/>
<fsSelection value="00000000 01000000"/>
<usFirstCharIndex value="65"/>
<usLastCharIndex value="68"/>
<sTypoAscender value="800"/>
<sTypoDescender value="-200"/>
<sTypoLineGap value="200"/>
<usWinAscent value="1000"/>
<usWinDescent value="200"/>
<ulCodePageRange1 value="00000000 00000000 00000000 00000001"/>
<ulCodePageRange2 value="00000000 00000000 00000000 00000000"/>
<sxHeight value="500"/>
<sCapHeight value="700"/>
<usDefaultChar value="0"/>
<usBreakChar value="32"/>
<usMaxContext value="2"/>
</OS_2>
<hmtx>
<mtx name=".notdef" width="500" lsb="50"/>
<mtx name="A" width="500" lsb="0"/>
<mtx name="B" width="500" lsb="0"/>
<mtx name="C" width="500" lsb="0"/>
<mtx name="D" width="500" lsb="0"/>
</hmtx>
<cmap>
<tableVersion version="0"/>
<cmap_format_4 platformID="0" platEncID="3" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
<map code="0x42" name="B"/><!-- LATIN CAPITAL LETTER B -->
<map code="0x43" name="C"/><!-- LATIN CAPITAL LETTER C -->
<map code="0x44" name="D"/><!-- LATIN CAPITAL LETTER D -->
</cmap_format_4>
<cmap_format_4 platformID="3" platEncID="1" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
<map code="0x42" name="B"/><!-- LATIN CAPITAL LETTER B -->
<map code="0x43" name="C"/><!-- LATIN CAPITAL LETTER C -->
<map code="0x44" name="D"/><!-- LATIN CAPITAL LETTER D -->
</cmap_format_4>
</cmap>
<loca>
<!-- The 'loca' table will be calculated by the compiler -->
</loca>
<glyf>
<!-- The xMin, yMin, xMax and yMax values
will be recalculated by the compiler. -->
<TTGlyph name=".notdef" xMin="50" yMin="-200" xMax="450" yMax="800">
<contour>
<pt x="50" y="-200" on="1"/>
<pt x="450" y="-200" on="1"/>
<pt x="450" y="800" on="1"/>
<pt x="50" y="800" on="1"/>
</contour>
<contour>
<pt x="100" y="-150" on="1"/>
<pt x="100" y="750" on="1"/>
<pt x="400" y="750" on="1"/>
<pt x="400" y="-150" on="1"/>
</contour>
<instructions/>
</TTGlyph>
<TTGlyph name="A"/><!-- contains no outline data -->
<TTGlyph name="B"/><!-- contains no outline data -->
<TTGlyph name="C"/><!-- contains no outline data -->
<TTGlyph name="D"/><!-- contains no outline data -->
</glyf>
<name>
<namerecord nameID="1" platformID="3" platEncID="1" langID="0x409">
Test
</namerecord>
<namerecord nameID="2" platformID="3" platEncID="1" langID="0x409">
Regular
</namerecord>
<namerecord nameID="3" platformID="3" platEncID="1" langID="0x409">
0.000;NONE;Test-Regular
</namerecord>
<namerecord nameID="4" platformID="3" platEncID="1" langID="0x409">
Test Regular
</namerecord>
<namerecord nameID="5" platformID="3" platEncID="1" langID="0x409">
Version 0.000
</namerecord>
<namerecord nameID="6" platformID="3" platEncID="1" langID="0x409">
Test-Regular
</namerecord>
</name>
<post>
<formatType value="2.0"/>
<italicAngle value="0.0"/>
<underlinePosition value="-150"/>
<underlineThickness value="50"/>
<isFixedPitch value="0"/>
<minMemType42 value="0"/>
<maxMemType42 value="0"/>
<minMemType1 value="0"/>
<maxMemType1 value="0"/>
<psNames>
<!-- This file uses unique glyph names based on the information
found in the 'post' table. Since these names might not be unique,
we have to invent artificial names in case of clashes. In order to
be able to retain the original information, we need a name to
ps name mapping for those cases where they differ. That's what
you see below.
-->
</psNames>
<extraNames>
<!-- following are the name that are not taken from the standard Mac glyph order -->
</extraNames>
</post>
<GPOS>
<Version value="0x00010000"/>
<ScriptList>
<!-- ScriptCount=1 -->
<ScriptRecord index="0">
<ScriptTag value="DFLT"/>
<Script>
<DefaultLangSys>
<ReqFeatureIndex value="65535"/>
<!-- FeatureCount=1 -->
<FeatureIndex index="0" value="0"/>
</DefaultLangSys>
<!-- LangSysCount=0 -->
</Script>
</ScriptRecord>
</ScriptList>
<FeatureList>
<!-- FeatureCount=1 -->
<FeatureRecord index="0">
<FeatureTag value="kern"/>
<Feature>
<!-- LookupCount=1 -->
<LookupListIndex index="0" value="0"/>
</Feature>
</FeatureRecord>
</FeatureList>
<LookupList>
<!-- LookupCount=1 -->
<Lookup index="0">
<LookupType value="2"/>
<LookupFlag value="8"/>
<!-- SubTableCount=1 -->
<PairPos index="0" Format="2">
<Coverage Format="1">
<Glyph value="A"/>
</Coverage>
<ValueFormat1 value="4"/>
<ValueFormat2 value="0"/>
<ClassDef1 Format="2">
</ClassDef1>
<ClassDef2 Format="1">
<ClassDef glyph="B" class="2"/>
<ClassDef glyph="D" class="1"/>
</ClassDef2>
<!-- Class1Count=1 -->
<!-- Class2Count=3 -->
<Class1Record index="0">
<Class2Record index="0">
<Value1 XAdvance="0"/>
</Class2Record>
<Class2Record index="1">
<Value1 XAdvance="-20"/>
</Class2Record>
<Class2Record index="2">
<Value1 XAdvance="-20"/>
</Class2Record>
</Class1Record>
</PairPos>
</Lookup>
</LookupList>
</GPOS>
</ttFont>

View File

@ -0,0 +1,304 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="\x00\x01\x00\x00" ttLibVersion="3.41">
<GlyphOrder>
<!-- The 'id' attribute is only for humans; it is ignored when parsed. -->
<GlyphID id="0" name=".notdef"/>
<GlyphID id="1" name="A"/>
<GlyphID id="2" name="B"/>
<GlyphID id="3" name="C"/>
<GlyphID id="4" name="D"/>
</GlyphOrder>
<head>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="1.0"/>
<fontRevision value="0.0"/>
<checkSumAdjustment value="0x330c9492"/>
<magicNumber value="0x5f0f3cf5"/>
<flags value="00000000 00000011"/>
<unitsPerEm value="1000"/>
<created value="Wed Jun 12 15:33:01 2019"/>
<modified value="Wed Jun 12 15:33:01 2019"/>
<xMin value="50"/>
<yMin value="-200"/>
<xMax value="450"/>
<yMax value="800"/>
<macStyle value="00000000 00000000"/>
<lowestRecPPEM value="6"/>
<fontDirectionHint value="2"/>
<indexToLocFormat value="0"/>
<glyphDataFormat value="0"/>
</head>
<hhea>
<tableVersion value="0x00010000"/>
<ascent value="1000"/>
<descent value="-200"/>
<lineGap value="0"/>
<advanceWidthMax value="500"/>
<minLeftSideBearing value="50"/>
<minRightSideBearing value="50"/>
<xMaxExtent value="450"/>
<caretSlopeRise value="1"/>
<caretSlopeRun value="0"/>
<caretOffset value="0"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="1"/>
</hhea>
<maxp>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="0x10000"/>
<numGlyphs value="5"/>
<maxPoints value="8"/>
<maxContours value="2"/>
<maxCompositePoints value="0"/>
<maxCompositeContours value="0"/>
<maxZones value="1"/>
<maxTwilightPoints value="0"/>
<maxStorage value="0"/>
<maxFunctionDefs value="0"/>
<maxInstructionDefs value="0"/>
<maxStackElements value="0"/>
<maxSizeOfInstructions value="0"/>
<maxComponentElements value="0"/>
<maxComponentDepth value="0"/>
</maxp>
<OS_2>
<!-- The fields 'usFirstCharIndex' and 'usLastCharIndex'
will be recalculated by the compiler -->
<version value="4"/>
<xAvgCharWidth value="500"/>
<usWeightClass value="400"/>
<usWidthClass value="5"/>
<fsType value="00000000 00000100"/>
<ySubscriptXSize value="650"/>
<ySubscriptYSize value="600"/>
<ySubscriptXOffset value="0"/>
<ySubscriptYOffset value="75"/>
<ySuperscriptXSize value="650"/>
<ySuperscriptYSize value="600"/>
<ySuperscriptXOffset value="0"/>
<ySuperscriptYOffset value="350"/>
<yStrikeoutSize value="50"/>
<yStrikeoutPosition value="300"/>
<sFamilyClass value="0"/>
<panose>
<bFamilyType value="0"/>
<bSerifStyle value="0"/>
<bWeight value="0"/>
<bProportion value="0"/>
<bContrast value="0"/>
<bStrokeVariation value="0"/>
<bArmStyle value="0"/>
<bLetterForm value="0"/>
<bMidline value="0"/>
<bXHeight value="0"/>
</panose>
<ulUnicodeRange1 value="00000000 00000000 00000000 00000001"/>
<ulUnicodeRange2 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange3 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/>
<achVendID value="NONE"/>
<fsSelection value="00000000 01000000"/>
<usFirstCharIndex value="65"/>
<usLastCharIndex value="68"/>
<sTypoAscender value="800"/>
<sTypoDescender value="-200"/>
<sTypoLineGap value="200"/>
<usWinAscent value="1000"/>
<usWinDescent value="200"/>
<ulCodePageRange1 value="00000000 00000000 00000000 00000001"/>
<ulCodePageRange2 value="00000000 00000000 00000000 00000000"/>
<sxHeight value="500"/>
<sCapHeight value="700"/>
<usDefaultChar value="0"/>
<usBreakChar value="32"/>
<usMaxContext value="2"/>
</OS_2>
<hmtx>
<mtx name=".notdef" width="500" lsb="50"/>
<mtx name="A" width="500" lsb="0"/>
<mtx name="B" width="500" lsb="0"/>
<mtx name="C" width="500" lsb="0"/>
<mtx name="D" width="500" lsb="0"/>
</hmtx>
<cmap>
<tableVersion version="0"/>
<cmap_format_4 platformID="0" platEncID="3" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
<map code="0x42" name="B"/><!-- LATIN CAPITAL LETTER B -->
<map code="0x43" name="C"/><!-- LATIN CAPITAL LETTER C -->
<map code="0x44" name="D"/><!-- LATIN CAPITAL LETTER D -->
</cmap_format_4>
<cmap_format_4 platformID="3" platEncID="1" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
<map code="0x42" name="B"/><!-- LATIN CAPITAL LETTER B -->
<map code="0x43" name="C"/><!-- LATIN CAPITAL LETTER C -->
<map code="0x44" name="D"/><!-- LATIN CAPITAL LETTER D -->
</cmap_format_4>
</cmap>
<loca>
<!-- The 'loca' table will be calculated by the compiler -->
</loca>
<glyf>
<!-- The xMin, yMin, xMax and yMax values
will be recalculated by the compiler. -->
<TTGlyph name=".notdef" xMin="50" yMin="-200" xMax="450" yMax="800">
<contour>
<pt x="50" y="-200" on="1"/>
<pt x="450" y="-200" on="1"/>
<pt x="450" y="800" on="1"/>
<pt x="50" y="800" on="1"/>
</contour>
<contour>
<pt x="100" y="-150" on="1"/>
<pt x="100" y="750" on="1"/>
<pt x="400" y="750" on="1"/>
<pt x="400" y="-150" on="1"/>
</contour>
<instructions/>
</TTGlyph>
<TTGlyph name="A"/><!-- contains no outline data -->
<TTGlyph name="B"/><!-- contains no outline data -->
<TTGlyph name="C"/><!-- contains no outline data -->
<TTGlyph name="D"/><!-- contains no outline data -->
</glyf>
<name>
<namerecord nameID="1" platformID="3" platEncID="1" langID="0x409">
Test Black
</namerecord>
<namerecord nameID="2" platformID="3" platEncID="1" langID="0x409">
Regular
</namerecord>
<namerecord nameID="3" platformID="3" platEncID="1" langID="0x409">
0.000;NONE;Test-Black
</namerecord>
<namerecord nameID="4" platformID="3" platEncID="1" langID="0x409">
Test Black
</namerecord>
<namerecord nameID="5" platformID="3" platEncID="1" langID="0x409">
Version 0.000
</namerecord>
<namerecord nameID="6" platformID="3" platEncID="1" langID="0x409">
Test-Black
</namerecord>
<namerecord nameID="16" platformID="3" platEncID="1" langID="0x409">
Test
</namerecord>
<namerecord nameID="17" platformID="3" platEncID="1" langID="0x409">
Black
</namerecord>
</name>
<post>
<formatType value="2.0"/>
<italicAngle value="0.0"/>
<underlinePosition value="-150"/>
<underlineThickness value="50"/>
<isFixedPitch value="0"/>
<minMemType42 value="0"/>
<maxMemType42 value="0"/>
<minMemType1 value="0"/>
<maxMemType1 value="0"/>
<psNames>
<!-- This file uses unique glyph names based on the information
found in the 'post' table. Since these names might not be unique,
we have to invent artificial names in case of clashes. In order to
be able to retain the original information, we need a name to
ps name mapping for those cases where they differ. That's what
you see below.
-->
</psNames>
<extraNames>
<!-- following are the name that are not taken from the standard Mac glyph order -->
</extraNames>
</post>
<GPOS>
<Version value="0x00010000"/>
<ScriptList>
<!-- ScriptCount=1 -->
<ScriptRecord index="0">
<ScriptTag value="DFLT"/>
<Script>
<DefaultLangSys>
<ReqFeatureIndex value="65535"/>
<!-- FeatureCount=1 -->
<FeatureIndex index="0" value="0"/>
</DefaultLangSys>
<!-- LangSysCount=0 -->
</Script>
</ScriptRecord>
</ScriptList>
<FeatureList>
<!-- FeatureCount=1 -->
<FeatureRecord index="0">
<FeatureTag value="kern"/>
<Feature>
<!-- LookupCount=1 -->
<LookupListIndex index="0" value="0"/>
</Feature>
</FeatureRecord>
</FeatureList>
<LookupList>
<!-- LookupCount=1 -->
<Lookup index="0">
<LookupType value="2"/>
<LookupFlag value="8"/>
<!-- SubTableCount=1 -->
<PairPos index="0" Format="2">
<Coverage Format="1">
<Glyph value="A"/>
<Glyph value="B"/>
</Coverage>
<ValueFormat1 value="4"/>
<ValueFormat2 value="0"/>
<ClassDef1 Format="1">
<ClassDef glyph="A" class="1"/>
</ClassDef1>
<ClassDef2 Format="1">
<ClassDef glyph="D" class="1"/>
</ClassDef2>
<!-- Class1Count=2 -->
<!-- Class2Count=2 -->
<Class1Record index="0">
<Class2Record index="0">
<Value1 XAdvance="0"/>
</Class2Record>
<Class2Record index="1">
<Value1 XAdvance="40"/>
</Class2Record>
</Class1Record>
<Class1Record index="1">
<Class2Record index="0">
<Value1 XAdvance="0"/>
</Class2Record>
<Class2Record index="1">
<Value1 XAdvance="40"/>
</Class2Record>
</Class1Record>
</PairPos>
</Lookup>
</LookupList>
</GPOS>
</ttFont>

View File

@ -0,0 +1,233 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="OTTO" ttLibVersion="3.41">
<GlyphOrder>
<!-- The 'id' attribute is only for humans; it is ignored when parsed. -->
<GlyphID id="0" name=".notdef"/>
<GlyphID id="1" name="A"/>
</GlyphOrder>
<head>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="1.0"/>
<fontRevision value="1.01"/>
<checkSumAdjustment value="0xeb345d38"/>
<magicNumber value="0x5f0f3cf5"/>
<flags value="00000000 00000011"/>
<unitsPerEm value="1000"/>
<created value="Thu Nov 29 14:52:09 2018"/>
<modified value="Thu Nov 29 14:52:09 2018"/>
<xMin value="50"/>
<yMin value="-115"/>
<xMax value="550"/>
<yMax value="762"/>
<macStyle value="00000000 00000000"/>
<lowestRecPPEM value="3"/>
<fontDirectionHint value="2"/>
<indexToLocFormat value="0"/>
<glyphDataFormat value="0"/>
</head>
<hhea>
<tableVersion value="0x00010000"/>
<ascent value="984"/>
<descent value="-273"/>
<lineGap value="0"/>
<advanceWidthMax value="600"/>
<minLeftSideBearing value="50"/>
<minRightSideBearing value="50"/>
<xMaxExtent value="550"/>
<caretSlopeRise value="1"/>
<caretSlopeRun value="0"/>
<caretOffset value="0"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="5"/>
</hhea>
<maxp>
<tableVersion value="0x5000"/>
<numGlyphs value="5"/>
</maxp>
<OS_2>
<!-- The fields 'usFirstCharIndex' and 'usLastCharIndex'
will be recalculated by the compiler -->
<version value="3"/>
<xAvgCharWidth value="578"/>
<usWeightClass value="200"/>
<usWidthClass value="5"/>
<fsType value="00000000 00000000"/>
<ySubscriptXSize value="650"/>
<ySubscriptYSize value="600"/>
<ySubscriptXOffset value="0"/>
<ySubscriptYOffset value="75"/>
<ySuperscriptXSize value="650"/>
<ySuperscriptYSize value="600"/>
<ySuperscriptXOffset value="0"/>
<ySuperscriptYOffset value="350"/>
<yStrikeoutSize value="50"/>
<yStrikeoutPosition value="286"/>
<sFamilyClass value="0"/>
<panose>
<bFamilyType value="2"/>
<bSerifStyle value="11"/>
<bWeight value="3"/>
<bProportion value="9"/>
<bContrast value="3"/>
<bStrokeVariation value="4"/>
<bArmStyle value="3"/>
<bLetterForm value="2"/>
<bMidline value="2"/>
<bXHeight value="4"/>
</panose>
<ulUnicodeRange1 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange2 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange3 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/>
<achVendID value="ADBO"/>
<fsSelection value="00000000 00000000"/>
<usFirstCharIndex value="36"/>
<usLastCharIndex value="84"/>
<sTypoAscender value="750"/>
<sTypoDescender value="-250"/>
<sTypoLineGap value="0"/>
<usWinAscent value="984"/>
<usWinDescent value="273"/>
<ulCodePageRange1 value="00000000 00000000 00000000 00000001"/>
<ulCodePageRange2 value="00000000 00000000 00000000 00000000"/>
<sxHeight value="478"/>
<sCapHeight value="660"/>
<usDefaultChar value="0"/>
<usBreakChar value="32"/>
<usMaxContext value="1"/>
</OS_2>
<name>
<namerecord nameID="1" platformID="1" platEncID="0" langID="0x0" unicode="True">
Source Code Variable
</namerecord>
<namerecord nameID="2" platformID="1" platEncID="0" langID="0x0" unicode="True">
Regular
</namerecord>
<namerecord nameID="3" platformID="1" platEncID="0" langID="0x0" unicode="True">
1.010;ADBO;SourceCode_ExtraLight
</namerecord>
<namerecord nameID="4" platformID="1" platEncID="0" langID="0x0" unicode="True">
Source Code Variable
</namerecord>
<namerecord nameID="5" platformID="1" platEncID="0" langID="0x0" unicode="True">
Version 1.010;hotconv 1.0.109;makeotfexe 2.5.65596
</namerecord>
<namerecord nameID="6" platformID="1" platEncID="0" langID="0x0" unicode="True">
SourceCode_ExtraLight
</namerecord>
<namerecord nameID="17" platformID="1" platEncID="0" langID="0x0" unicode="True">
Roman Master 0
</namerecord>
<namerecord nameID="1" platformID="3" platEncID="1" langID="0x409">
Source Code Variable
</namerecord>
<namerecord nameID="2" platformID="3" platEncID="1" langID="0x409">
Regular
</namerecord>
<namerecord nameID="3" platformID="3" platEncID="1" langID="0x409">
1.010;ADBO;SourceCode_ExtraLight
</namerecord>
<namerecord nameID="4" platformID="3" platEncID="1" langID="0x409">
Source Code Variable
</namerecord>
<namerecord nameID="5" platformID="3" platEncID="1" langID="0x409">
Version 1.010;hotconv 1.0.109;makeotfexe 2.5.65596
</namerecord>
<namerecord nameID="6" platformID="3" platEncID="1" langID="0x409">
SourceCode_ExtraLight
</namerecord>
<namerecord nameID="17" platformID="3" platEncID="1" langID="0x409">
Roman Master 0
</namerecord>
</name>
<cmap>
<tableVersion version="0"/>
<cmap_format_4 platformID="0" platEncID="3" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
</cmap_format_4>
<cmap_format_6 platformID="1" platEncID="0" language="0">
<map code="0x41" name="A"/>
</cmap_format_6>
<cmap_format_4 platformID="3" platEncID="1" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
</cmap_format_4>
</cmap>
<post>
<formatType value="3.0"/>
<italicAngle value="0.0"/>
<underlinePosition value="-75"/>
<underlineThickness value="50"/>
<isFixedPitch value="1"/>
<minMemType42 value="0"/>
<maxMemType42 value="0"/>
<minMemType1 value="0"/>
<maxMemType1 value="0"/>
</post>
<CFF>
<major value="1"/>
<minor value="0"/>
<CFFFont name="SourceCode_ExtraLight">
<version value="1.0"/>
<Notice value="Source is a trademark of Adobe Systems Incorporated in the United States and/or other countries."/>
<Copyright value="Copyright 2010 - 2012 Adobe Systems Incorporated. All Rights Reserved."/>
<FamilyName value="Source Code"/>
<isFixedPitch value="1"/>
<ItalicAngle value="0"/>
<UnderlinePosition value="-100"/>
<UnderlineThickness value="50"/>
<PaintType value="0"/>
<CharstringType value="2"/>
<FontMatrix value="0.001 0 0 0.001 0 0"/>
<FontBBox value="50 -115 550 762"/>
<StrokeWidth value="0"/>
<!-- charset is dumped separately as the 'GlyphOrder' element -->
<Encoding name="StandardEncoding"/>
<Private>
<BlueValues value="-12 0 478 490 570 582 640 652 660 672 722 734"/>
<OtherBlues value="-234 -222"/>
<BlueScale value="0.0625"/>
<BlueShift value="7"/>
<BlueFuzz value="0"/>
<StdHW value="28"/>
<StdVW value="34"/>
<ForceBold value="0"/>
<LanguageGroup value="0"/>
<ExpansionFactor value="0.06"/>
<initialRandomSeed value="0"/>
<defaultWidthX value="600"/>
<nominalWidthX value="597"/>
</Private>
<CharStrings>
<CharString name=".notdef">
endchar
</CharString>
<CharString name="A">
endchar
</CharString>
= </CharStrings>
</CFFFont>
<GlobalSubrs>
<!-- The 'index' attribute is only for humans; it is ignored when parsed. -->
</GlobalSubrs>
</CFF>
<hmtx>
<mtx name=".notdef" width="600" lsb="84"/>
<mtx name="A" width="600" lsb="50"/>
</hmtx>
</ttFont>

View File

@ -0,0 +1,233 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="OTTO" ttLibVersion="3.41">
<GlyphOrder>
<!-- The 'id' attribute is only for humans; it is ignored when parsed. -->
<GlyphID id="0" name=".notdef"/>
<GlyphID id="1" name="A"/>
</GlyphOrder>
<head>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="1.0"/>
<fontRevision value="1.01"/>
<checkSumAdjustment value="0x60d07155"/>
<magicNumber value="0x5f0f3cf5"/>
<flags value="00000000 00000011"/>
<unitsPerEm value="1000"/>
<created value="Thu Nov 29 14:52:09 2018"/>
<modified value="Thu Nov 29 14:52:09 2018"/>
<xMin value="31"/>
<yMin value="-115"/>
<xMax value="569"/>
<yMax value="751"/>
<macStyle value="00000000 00000000"/>
<lowestRecPPEM value="3"/>
<fontDirectionHint value="2"/>
<indexToLocFormat value="0"/>
<glyphDataFormat value="0"/>
</head>
<hhea>
<tableVersion value="0x00010000"/>
<ascent value="984"/>
<descent value="-273"/>
<lineGap value="0"/>
<advanceWidthMax value="600"/>
<minLeftSideBearing value="31"/>
<minRightSideBearing value="31"/>
<xMaxExtent value="569"/>
<caretSlopeRise value="1"/>
<caretSlopeRun value="0"/>
<caretOffset value="0"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="5"/>
</hhea>
<maxp>
<tableVersion value="0x5000"/>
<numGlyphs value="5"/>
</maxp>
<OS_2>
<!-- The fields 'usFirstCharIndex' and 'usLastCharIndex'
will be recalculated by the compiler -->
<version value="3"/>
<xAvgCharWidth value="579"/>
<usWeightClass value="400"/>
<usWidthClass value="5"/>
<fsType value="00000000 00000000"/>
<ySubscriptXSize value="650"/>
<ySubscriptYSize value="600"/>
<ySubscriptXOffset value="0"/>
<ySubscriptYOffset value="75"/>
<ySuperscriptXSize value="650"/>
<ySuperscriptYSize value="600"/>
<ySuperscriptXOffset value="0"/>
<ySuperscriptYOffset value="350"/>
<yStrikeoutSize value="50"/>
<yStrikeoutPosition value="291"/>
<sFamilyClass value="0"/>
<panose>
<bFamilyType value="2"/>
<bSerifStyle value="11"/>
<bWeight value="5"/>
<bProportion value="9"/>
<bContrast value="3"/>
<bStrokeVariation value="4"/>
<bArmStyle value="3"/>
<bLetterForm value="2"/>
<bMidline value="2"/>
<bXHeight value="4"/>
</panose>
<ulUnicodeRange1 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange2 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange3 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/>
<achVendID value="ADBO"/>
<fsSelection value="00000000 01000000"/>
<usFirstCharIndex value="36"/>
<usLastCharIndex value="84"/>
<sTypoAscender value="750"/>
<sTypoDescender value="-250"/>
<sTypoLineGap value="0"/>
<usWinAscent value="984"/>
<usWinDescent value="273"/>
<ulCodePageRange1 value="00000000 00000000 00000000 00000001"/>
<ulCodePageRange2 value="00000000 00000000 00000000 00000000"/>
<sxHeight value="486"/>
<sCapHeight value="660"/>
<usDefaultChar value="0"/>
<usBreakChar value="32"/>
<usMaxContext value="1"/>
</OS_2>
<name>
<namerecord nameID="1" platformID="1" platEncID="0" langID="0x0" unicode="True">
Source Code Variable
</namerecord>
<namerecord nameID="2" platformID="1" platEncID="0" langID="0x0" unicode="True">
Regular
</namerecord>
<namerecord nameID="3" platformID="1" platEncID="0" langID="0x0" unicode="True">
1.010;ADBO;SourceCodeVariable-Roman
</namerecord>
<namerecord nameID="4" platformID="1" platEncID="0" langID="0x0" unicode="True">
Source Code Variable
</namerecord>
<namerecord nameID="5" platformID="1" platEncID="0" langID="0x0" unicode="True">
Version 1.010;hotconv 1.0.109;makeotfexe 2.5.65596
</namerecord>
<namerecord nameID="6" platformID="1" platEncID="0" langID="0x0" unicode="True">
SourceCodeVariable-Roman
</namerecord>
<namerecord nameID="17" platformID="1" platEncID="0" langID="0x0" unicode="True">
Roman
</namerecord>
<namerecord nameID="1" platformID="3" platEncID="1" langID="0x409">
Source Code Variable
</namerecord>
<namerecord nameID="2" platformID="3" platEncID="1" langID="0x409">
Regular
</namerecord>
<namerecord nameID="3" platformID="3" platEncID="1" langID="0x409">
1.010;ADBO;SourceCodeVariable-Roman
</namerecord>
<namerecord nameID="4" platformID="3" platEncID="1" langID="0x409">
Source Code Variable
</namerecord>
<namerecord nameID="5" platformID="3" platEncID="1" langID="0x409">
Version 1.010;hotconv 1.0.109;makeotfexe 2.5.65596
</namerecord>
<namerecord nameID="6" platformID="3" platEncID="1" langID="0x409">
SourceCodeVariable-Roman
</namerecord>
<namerecord nameID="17" platformID="3" platEncID="1" langID="0x409">
Roman
</namerecord>
</name>
<cmap>
<tableVersion version="0"/>
<cmap_format_4 platformID="0" platEncID="3" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
</cmap_format_4>
<cmap_format_6 platformID="1" platEncID="0" language="0">
<map code="0x41" name="A"/>
</cmap_format_6>
<cmap_format_4 platformID="3" platEncID="1" language="0">
<map code="0x41" name="A"/><!-- LATIN CAPITAL LETTER A -->
</cmap_format_4>
</cmap>
<post>
<formatType value="3.0"/>
<italicAngle value="0.0"/>
<underlinePosition value="-75"/>
<underlineThickness value="50"/>
<isFixedPitch value="1"/>
<minMemType42 value="0"/>
<maxMemType42 value="0"/>
<minMemType1 value="0"/>
<maxMemType1 value="0"/>
</post>
<CFF>
<major value="1"/>
<minor value="0"/>
<CFFFont name="SourceCodeVariable-Roman">
<version value="1.0"/>
<Notice value="Source is a trademark of Adobe Systems Incorporated in the United States and/or other countries."/>
<Copyright value="Copyright 2010 - 2012 Adobe Systems Incorporated. All Rights Reserved."/>
<FamilyName value="Source Code"/>
<isFixedPitch value="1"/>
<ItalicAngle value="0"/>
<UnderlinePosition value="-100"/>
<UnderlineThickness value="50"/>
<PaintType value="0"/>
<CharstringType value="2"/>
<FontMatrix value="0.001 0 0 0.001 0 0"/>
<FontBBox value="31 -115 569 751"/>
<StrokeWidth value="0"/>
<!-- charset is dumped separately as the 'GlyphOrder' element -->
<Encoding name="StandardEncoding"/>
<Private>
<BlueValues value="-12 0 486 498 574 586 638 650 656 668 712 724"/>
<OtherBlues value="-217 -205"/>
<BlueScale value="0.0625"/>
<BlueShift value="7"/>
<BlueFuzz value="0"/>
<StdHW value="67"/>
<StdVW value="85"/>
<ForceBold value="0"/>
<LanguageGroup value="0"/>
<ExpansionFactor value="0.06"/>
<initialRandomSeed value="0"/>
<defaultWidthX value="600"/>
<nominalWidthX value="604"/>
</Private>
<CharStrings>
<CharString name=".notdef">
endchar
</CharString>
<CharString name="A">
endchar
</CharString>
</CharStrings>
</CFFFont>
<GlobalSubrs>
<!-- The 'index' attribute is only for humans; it is ignored when parsed. -->
</GlobalSubrs>
</CFF>
<hmtx>
<mtx name=".notdef" width="600" lsb="62"/>
<mtx name="A" width="600" lsb="31"/>
</hmtx>
</ttFont>

View File

@ -0,0 +1,485 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="OTTO" ttLibVersion="3.42">
<GlyphOrder>
<!-- The 'id' attribute is only for humans; it is ignored when parsed. -->
<GlyphID id="0" name=".notdef"/>
<GlyphID id="1" name="uni3001"/>
<GlyphID id="2" name="uni30FB"/>
<GlyphID id="3" name="uniFF1A"/>
<GlyphID id="4" name="uniFF2D"/>
<GlyphID id="5" name="uni3073"/>
<GlyphID id="6" name="uni3074"/>
<GlyphID id="7" name="uni307B"/>
</GlyphOrder>
<head>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="1.0"/>
<fontRevision value="1.004"/>
<checkSumAdjustment value="0x90c6f91d"/>
<magicNumber value="0x5f0f3cf5"/>
<flags value="00000000 00000011"/>
<unitsPerEm value="1000"/>
<created value="Wed Jun 5 14:40:00 2019"/>
<modified value="Tue Jun 11 21:27:36 2019"/>
<xMin value="64"/>
<yMin value="-52"/>
<xMax value="974"/>
<yMax value="798"/>
<macStyle value="00000000 00000000"/>
<lowestRecPPEM value="3"/>
<fontDirectionHint value="2"/>
<indexToLocFormat value="0"/>
<glyphDataFormat value="0"/>
</head>
<hhea>
<tableVersion value="0x00010000"/>
<ascent value="1160"/>
<descent value="-317"/>
<lineGap value="0"/>
<advanceWidthMax value="1000"/>
<minLeftSideBearing value="64"/>
<minRightSideBearing value="26"/>
<xMaxExtent value="974"/>
<caretSlopeRise value="1"/>
<caretSlopeRun value="0"/>
<caretOffset value="0"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="2"/>
</hhea>
<maxp>
<tableVersion value="0x5000"/>
<numGlyphs value="8"/>
</maxp>
<OS_2>
<!-- The fields 'usFirstCharIndex' and 'usLastCharIndex'
will be recalculated by the compiler -->
<version value="3"/>
<xAvgCharWidth value="962"/>
<usWeightClass value="250"/>
<usWidthClass value="5"/>
<fsType value="00000000 00000100"/>
<ySubscriptXSize value="650"/>
<ySubscriptYSize value="600"/>
<ySubscriptXOffset value="0"/>
<ySubscriptYOffset value="75"/>
<ySuperscriptXSize value="650"/>
<ySuperscriptYSize value="600"/>
<ySuperscriptXOffset value="0"/>
<ySuperscriptYOffset value="350"/>
<yStrikeoutSize value="50"/>
<yStrikeoutPosition value="228"/>
<sFamilyClass value="0"/>
<panose>
<bFamilyType value="0"/>
<bSerifStyle value="0"/>
<bWeight value="3"/>
<bProportion value="0"/>
<bContrast value="0"/>
<bStrokeVariation value="0"/>
<bArmStyle value="0"/>
<bLetterForm value="0"/>
<bMidline value="0"/>
<bXHeight value="0"/>
</panose>
<ulUnicodeRange1 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange2 value="00000000 00000111 00000000 00000000"/>
<ulUnicodeRange3 value="00000000 00000000 00000000 00010000"/>
<ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/>
<achVendID value="UKWN"/>
<fsSelection value="00000000 00000000"/>
<usFirstCharIndex value="12289"/>
<usLastCharIndex value="65325"/>
<sTypoAscender value="880"/>
<sTypoDescender value="-120"/>
<sTypoLineGap value="200"/>
<usWinAscent value="1160"/>
<usWinDescent value="317"/>
<ulCodePageRange1 value="00100000 00000010 00000000 10011111"/>
<ulCodePageRange2 value="00000000 00000000 00000000 00000000"/>
<sxHeight value="380"/>
<sCapHeight value="760"/>
<usDefaultChar value="0"/>
<usBreakChar value="32"/>
<usMaxContext value="1"/>
</OS_2>
<name>
<namerecord nameID="0" platformID="3" platEncID="1" langID="0x409">
Copyright © 2018 Adobe systems Co., Ltd. All Rights Reserved.
</namerecord>
<namerecord nameID="1" platformID="3" platEncID="1" langID="0x409">
MasterSet_KanjiFullEX
</namerecord>
<namerecord nameID="2" platformID="3" platEncID="1" langID="0x409">
Regular
</namerecord>
<namerecord nameID="3" platformID="3" platEncID="1" langID="0x409">
1.004;UKWN;MasterSet_KanjiFullEX-w0.00
</namerecord>
<namerecord nameID="4" platformID="3" platEncID="1" langID="0x409">
MasterSet_KanjiFullEX
</namerecord>
<namerecord nameID="5" platformID="3" platEncID="1" langID="0x409">
Version 1.004;hotconv 1.0.109;makeotfexe 2.5.65596
</namerecord>
<namerecord nameID="6" platformID="3" platEncID="1" langID="0x409">
MasterSet_KanjiFullEX-w0.00
</namerecord>
</name>
<cmap>
<tableVersion version="0"/>
<cmap_format_4 platformID="0" platEncID="3" language="0">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_4>
<cmap_format_12 platformID="0" platEncID="4" format="12" reserved="0" length="88" language="0" nGroups="6">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_12>
<cmap_format_4 platformID="3" platEncID="1" language="0">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_4>
<cmap_format_12 platformID="3" platEncID="10" format="12" reserved="0" length="88" language="0" nGroups="6">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_12>
</cmap>
<post>
<formatType value="3.0"/>
<italicAngle value="0.0"/>
<underlinePosition value="-75"/>
<underlineThickness value="50"/>
<isFixedPitch value="0"/>
<minMemType42 value="0"/>
<maxMemType42 value="0"/>
<minMemType1 value="0"/>
<maxMemType1 value="0"/>
</post>
<CFF>
<major value="1"/>
<minor value="0"/>
<CFFFont name="MasterSet_KanjiFullEX-w0.00">
<FamilyName value="MasterSet_KanjiFullEX"/>
<isFixedPitch value="0"/>
<ItalicAngle value="0"/>
<UnderlinePosition value="-100"/>
<UnderlineThickness value="50"/>
<PaintType value="0"/>
<CharstringType value="2"/>
<FontMatrix value="0.001 0 0 0.001 0 0"/>
<FontBBox value="64 -52 974 798"/>
<StrokeWidth value="0"/>
<!-- charset is dumped separately as the 'GlyphOrder' element -->
<Encoding name="StandardEncoding"/>
<Private>
<BlueValues value="0 0"/>
<BlueScale value="0.039625"/>
<BlueShift value="7"/>
<BlueFuzz value="1"/>
<ForceBold value="0"/>
<LanguageGroup value="0"/>
<ExpansionFactor value="0.06"/>
<initialRandomSeed value="0"/>
<defaultWidthX value="1000"/>
<nominalWidthX value="532"/>
</Private>
<CharStrings>
<CharString name=".notdef">
-282 endchar
</CharString>
<CharString name="uni3001">
291 -43 rmoveto
29 24 rlineto
-74 84 -84 83 -73 58 rrcurveto
-25 -24 rlineto
72 -56 87 -85 68 -84 rrcurveto
endchar
</CharString>
<CharString name="uni3073">
706 699 rmoveto
-32 -10 rlineto
50 -192 56 -132 112 -115 rrcurveto
24 26 rlineto
-143 124 -45 182 -22 117 rrcurveto
-592 -57 rmoveto
3 -38 rlineto
18 2 18 3 17 2 rrcurveto
43 6 101 12 63 13 rrcurveto
-83 -80 -128 -166 0 -210 rrcurveto
0 -150 92 -88 154 0 rrcurveto
294 0 65 313 -48 302 rrcurveto
-29 79 rlineto
64 -402 -96 -263 -249 0 rrcurveto
-109 0 -110 48 0 166 rrcurveto
0 219 171 196 58 42 rrcurveto
14 5 30 6 12 3 rrcurveto
-9 30 rlineto
-52 -21 -170 -26 -83 -3 rrcurveto
-18 -1 -21 0 -12 1 rrcurveto
677 114 rmoveto
-26 -11 rlineto
22 -34 33 -63 20 -42 rrcurveto
30 14 rlineto
-21 41 -37 62 -21 33 rrcurveto
97 40 rmoveto
-26 -13 rlineto
24 -33 31 -59 21 -44 rrcurveto
30 14 rlineto
-23 43 -36 60 -21 32 rrcurveto
endchar
</CharString>
<CharString name="uni3074">
706 699 rmoveto
-32 -10 rlineto
50 -192 56 -132 112 -115 rrcurveto
24 26 rlineto
-143 124 -45 182 -22 117 rrcurveto
-592 -57 rmoveto
3 -38 rlineto
18 2 18 3 17 2 rrcurveto
43 6 101 12 63 13 rrcurveto
-83 -80 -128 -166 0 -210 rrcurveto
0 -150 92 -88 154 0 rrcurveto
294 0 65 313 -48 302 rrcurveto
-29 79 rlineto
64 -402 -96 -263 -249 0 rrcurveto
-109 0 -110 48 0 166 rrcurveto
0 219 171 196 58 42 rrcurveto
14 5 30 6 12 3 rrcurveto
-9 30 rlineto
-52 -21 -170 -26 -83 -3 rrcurveto
-18 -1 -21 0 -12 1 rrcurveto
681 51 rmoveto
0 42 33 33 41 0 rrcurveto
41 0 33 -33 0 -42 rrcurveto
0 -41 -33 -33 -41 0 rrcurveto
-42 0 -32 33 0 41 rrcurveto
-30 0 rmoveto
0 -57 46 -47 58 0 rrcurveto
57 0 48 47 0 57 rrcurveto
0 58 -48 47 -57 0 rrcurveto
-58 0 -46 -47 0 -58 rrcurveto
endchar
</CharString>
<CharString name="uni307B">
703 676 rmoveto
-28 0 rlineto
0 -63 0 -106 0 -61 rrcurveto
0 -103 14 -162 0 -52 rrcurveto
0 -59 -17 -50 -97 0 rrcurveto
-91 0 -58 31 0 63 rrcurveto
0 53 62 37 87 0 rrcurveto
125 0 119 -56 94 -98 rrcurveto
19 31 rlineto
-90 81 -113 69 -154 0 rrcurveto
-130 0 -47 -64 0 -53 rrcurveto
0 -80 70 -42 105 0 rrcurveto
85 0 58 36 0 74 rrcurveto
0 68 -13 166 0 113 rrcurveto
0 61 0 96 0 70 rrcurveto
-284 -213 rmoveto
0 -31 rlineto
168 -10 194 12 125 13 rrcurveto
0 31 rlineto
-129 -15 -187 -13 -171 13 rrcurveto
16 230 rmoveto
0 -30 rlineto
139 -7 200 11 108 11 rrcurveto
0 30 rlineto
-111 -15 -197 -11 -139 11 rrcurveto
-207 51 rmoveto
-37 4 rlineto
0 -11 -1 -14 -3 -19 rrcurveto
-13 -88 -37 -183 0 -143 rrcurveto
0 -135 16 -105 20 -74 rrcurveto
28 3 rlineto
-1 7 -2 12 -1 9 rrcurveto
-1 13 2 16 3 14 rrcurveto
9 43 39 105 22 55 rrcurveto
-20 17 rlineto
-20 -48 -32 -89 -18 -56 rrcurveto
-10 78 -5 58 0 78 rrcurveto
0 124 26 166 25 119 rrcurveto
3 18 4 13 4 13 rrcurveto
endchar
</CharString>
<CharString name="uni30FB">
500 465 rmoveto
-47 0 -38 -38 0 -47 rrcurveto
0 -47 38 -38 47 0 rrcurveto
47 0 38 38 0 47 rrcurveto
0 47 -38 38 -47 0 rrcurveto
endchar
</CharString>
<CharString name="uniFF1A">
500 572 rmoveto
28 0 28 19 0 37 rrcurveto
0 37 -28 19 -28 0 rrcurveto
-28 0 -28 -19 0 -37 rrcurveto
0 -37 28 -19 28 0 rrcurveto
0 -502 rmoveto
28 0 28 19 0 37 rrcurveto
0 37 -28 19 -28 0 rrcurveto
-28 0 -28 -19 0 -37 rrcurveto
0 -37 28 -19 28 0 rrcurveto
endchar
</CharString>
<CharString name="uniFF2D">
180 0 rmoveto
35 0 rlineto
0 502 rlineto
0 57 -1 74 -2 59 rrcurveto
5 0 rlineto
67 -160 rlineto
196 -451 rlineto
39 0 rlineto
195 451 rlineto
69 160 rlineto
5 0 rlineto
-2 -59 -3 -74 0 -57 rrcurveto
0 -502 rlineto
37 0 rlineto
0 726 rlineto
-59 0 rlineto
-191 -438 rlineto
-23 -54 -20 -55 -24 -55 rrcurveto
-4 0 rlineto
-24 55 -23 55 -23 54 rrcurveto
-190 438 rlineto
-59 0 rlineto
0 -726 rlineto
endchar
</CharString>
</CharStrings>
</CFFFont>
<GlobalSubrs>
<!-- The 'index' attribute is only for humans; it is ignored when parsed. -->
</GlobalSubrs>
</CFF>
<GPOS>
<Version value="0x00010000"/>
<ScriptList>
<!-- ScriptCount=1 -->
<ScriptRecord index="0">
<ScriptTag value="DFLT"/>
<Script>
<DefaultLangSys>
<ReqFeatureIndex value="65535"/>
<!-- FeatureCount=1 -->
<FeatureIndex index="0" value="0"/>
</DefaultLangSys>
<!-- LangSysCount=0 -->
</Script>
</ScriptRecord>
</ScriptList>
<FeatureList>
<!-- FeatureCount=1 -->
<FeatureRecord index="0">
<FeatureTag value="vpal"/>
<Feature>
<!-- LookupCount=1 -->
<LookupListIndex index="0" value="0"/>
</Feature>
</FeatureRecord>
</FeatureList>
<LookupList>
<!-- LookupCount=1 -->
<Lookup index="0">
<LookupType value="1"/>
<LookupFlag value="0"/>
<!-- SubTableCount=5 -->
<SinglePos index="0" Format="2">
<Coverage Format="1">
<Glyph value="uni3001"/>
<Glyph value="uniFF1A"/>
</Coverage>
<ValueFormat value="5"/>
<!-- ValueCount=2 -->
<Value index="0" XPlacement="-9" XAdvance="-500"/>
<Value index="1" XPlacement="-250" XAdvance="-500"/>
</SinglePos>
<SinglePos index="1" Format="2">
<Coverage Format="1">
<Glyph value="uni30FB"/>
</Coverage>
<ValueFormat value="7"/>
<!-- ValueCount=1 -->
<Value index="0" XPlacement="-250" YPlacement="1" XAdvance="-500"/>
</SinglePos>
<SinglePos index="2" Format="2">
<Coverage Format="1">
<Glyph value="uni3073"/>
<Glyph value="uni3074"/>
</Coverage>
<ValueFormat value="4"/>
<!-- ValueCount=2 -->
<Value index="0" XAdvance="-36"/>
<Value index="1" XAdvance="-30"/>
</SinglePos>
<SinglePos index="3" Format="2">
<Coverage Format="1">
<Glyph value="uni307B"/>
</Coverage>
<ValueFormat value="1"/>
<!-- ValueCount=1 -->
<Value index="0" XPlacement="11"/>
</SinglePos>
<SinglePos index="4" Format="2">
<Coverage Format="1">
<Glyph value="uniFF2D"/>
</Coverage>
<ValueFormat value="5"/>
<!-- ValueCount=1 -->
<Value index="0" XPlacement="12" XAdvance="23"/>
</SinglePos>
</Lookup>
</LookupList>
</GPOS>
<hmtx>
<mtx name=".notdef" width="250" lsb="0"/>
<mtx name="uni3001" width="1000" lsb="64"/>
<mtx name="uni3073" width="1000" lsb="114"/>
<mtx name="uni3074" width="1000" lsb="114"/>
<mtx name="uni307B" width="1000" lsb="137"/>
<mtx name="uni30FB" width="1000" lsb="415"/>
<mtx name="uniFF1A" width="1000" lsb="444"/>
<mtx name="uniFF2D" width="1000" lsb="180"/>
</hmtx>
</ttFont>

View File

@ -0,0 +1,473 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="OTTO" ttLibVersion="3.42">
<GlyphOrder>
<!-- The 'id' attribute is only for humans; it is ignored when parsed. -->
<GlyphID id="0" name=".notdef"/>
<GlyphID id="1" name="uni3001"/>
<GlyphID id="2" name="uni30FB"/>
<GlyphID id="3" name="uniFF1A"/>
<GlyphID id="4" name="uniFF2D"/>
<GlyphID id="5" name="uni3073"/>
<GlyphID id="6" name="uni3074"/>
<GlyphID id="7" name="uni307B"/>
</GlyphOrder>
<head>
<!-- Most of this table will be recalculated by the compiler -->
<tableVersion value="1.0"/>
<fontRevision value="1.004"/>
<checkSumAdjustment value="0xfa2dc49e"/>
<magicNumber value="0x5f0f3cf5"/>
<flags value="00000000 00000011"/>
<unitsPerEm value="1000"/>
<created value="Wed Jun 5 14:40:08 2019"/>
<modified value="Tue Jun 11 21:27:55 2019"/>
<xMin value="33"/>
<yMin value="-87"/>
<xMax value="992"/>
<yMax value="855"/>
<macStyle value="00000000 00000000"/>
<lowestRecPPEM value="3"/>
<fontDirectionHint value="2"/>
<indexToLocFormat value="0"/>
<glyphDataFormat value="0"/>
</head>
<hhea>
<tableVersion value="0x00010000"/>
<ascent value="1160"/>
<descent value="-317"/>
<lineGap value="0"/>
<advanceWidthMax value="1000"/>
<minLeftSideBearing value="33"/>
<minRightSideBearing value="8"/>
<xMaxExtent value="992"/>
<caretSlopeRise value="1"/>
<caretSlopeRun value="0"/>
<caretOffset value="0"/>
<reserved0 value="0"/>
<reserved1 value="0"/>
<reserved2 value="0"/>
<reserved3 value="0"/>
<metricDataFormat value="0"/>
<numberOfHMetrics value="2"/>
</hhea>
<maxp>
<tableVersion value="0x5000"/>
<numGlyphs value="8"/>
</maxp>
<OS_2>
<!-- The fields 'usFirstCharIndex' and 'usLastCharIndex'
will be recalculated by the compiler -->
<version value="3"/>
<xAvgCharWidth value="971"/>
<usWeightClass value="900"/>
<usWidthClass value="5"/>
<fsType value="00000000 00000100"/>
<ySubscriptXSize value="650"/>
<ySubscriptYSize value="600"/>
<ySubscriptXOffset value="0"/>
<ySubscriptYOffset value="75"/>
<ySuperscriptXSize value="650"/>
<ySuperscriptYSize value="600"/>
<ySuperscriptXOffset value="0"/>
<ySuperscriptYOffset value="350"/>
<yStrikeoutSize value="50"/>
<yStrikeoutPosition value="228"/>
<sFamilyClass value="0"/>
<panose>
<bFamilyType value="0"/>
<bSerifStyle value="0"/>
<bWeight value="10"/>
<bProportion value="0"/>
<bContrast value="0"/>
<bStrokeVariation value="0"/>
<bArmStyle value="0"/>
<bLetterForm value="0"/>
<bMidline value="0"/>
<bXHeight value="0"/>
</panose>
<ulUnicodeRange1 value="00000000 00000000 00000000 00000000"/>
<ulUnicodeRange2 value="00000000 00000111 00000000 00000000"/>
<ulUnicodeRange3 value="00000000 00000000 00000000 00010000"/>
<ulUnicodeRange4 value="00000000 00000000 00000000 00000000"/>
<achVendID value="UKWN"/>
<fsSelection value="00000000 00000000"/>
<usFirstCharIndex value="12289"/>
<usLastCharIndex value="65325"/>
<sTypoAscender value="880"/>
<sTypoDescender value="-120"/>
<sTypoLineGap value="200"/>
<usWinAscent value="1160"/>
<usWinDescent value="317"/>
<ulCodePageRange1 value="00100000 00000010 00000000 10011111"/>
<ulCodePageRange2 value="00000000 00000000 00000000 00000000"/>
<sxHeight value="380"/>
<sCapHeight value="760"/>
<usDefaultChar value="0"/>
<usBreakChar value="32"/>
<usMaxContext value="1"/>
</OS_2>
<name>
<namerecord nameID="0" platformID="3" platEncID="1" langID="0x409">
Copyright © 2018 Adobe systems Co., Ltd. All Rights Reserved.
</namerecord>
<namerecord nameID="1" platformID="3" platEncID="1" langID="0x409">
MasterSet_KanjiFullEX
</namerecord>
<namerecord nameID="2" platformID="3" platEncID="1" langID="0x409">
Regular
</namerecord>
<namerecord nameID="3" platformID="3" platEncID="1" langID="0x409">
1.004;UKWN;MasterSet_KanjiFullEX-w1000.00
</namerecord>
<namerecord nameID="4" platformID="3" platEncID="1" langID="0x409">
MasterSet_KanjiFullEX
</namerecord>
<namerecord nameID="5" platformID="3" platEncID="1" langID="0x409">
Version 1.004;hotconv 1.0.109;makeotfexe 2.5.65596
</namerecord>
<namerecord nameID="6" platformID="3" platEncID="1" langID="0x409">
MasterSet_KanjiFullEX-w1000.00
</namerecord>
</name>
<cmap>
<tableVersion version="0"/>
<cmap_format_4 platformID="0" platEncID="3" language="0">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_4>
<cmap_format_12 platformID="0" platEncID="4" format="12" reserved="0" length="88" language="0" nGroups="6">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_12>
<cmap_format_4 platformID="3" platEncID="1" language="0">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_4>
<cmap_format_12 platformID="3" platEncID="10" format="12" reserved="0" length="88" language="0" nGroups="6">
<map code="0x3001" name="uni3001"/><!-- IDEOGRAPHIC COMMA -->
<map code="0x3073" name="uni3073"/><!-- HIRAGANA LETTER BI -->
<map code="0x3074" name="uni3074"/><!-- HIRAGANA LETTER PI -->
<map code="0x307b" name="uni307B"/><!-- HIRAGANA LETTER HO -->
<map code="0x30fb" name="uni30FB"/><!-- KATAKANA MIDDLE DOT -->
<map code="0xff1a" name="uniFF1A"/><!-- FULLWIDTH COLON -->
<map code="0xff2d" name="uniFF2D"/><!-- FULLWIDTH LATIN CAPITAL LETTER M -->
</cmap_format_12>
</cmap>
<post>
<formatType value="3.0"/>
<italicAngle value="0.0"/>
<underlinePosition value="-75"/>
<underlineThickness value="50"/>
<isFixedPitch value="0"/>
<minMemType42 value="0"/>
<maxMemType42 value="0"/>
<minMemType1 value="0"/>
<maxMemType1 value="0"/>
</post>
<CFF>
<major value="1"/>
<minor value="0"/>
<CFFFont name="MasterSet_KanjiFullEX-w1000.00">
<FamilyName value="MasterSet_KanjiFullEX"/>
<isFixedPitch value="0"/>
<ItalicAngle value="0"/>
<UnderlinePosition value="-100"/>
<UnderlineThickness value="50"/>
<PaintType value="0"/>
<CharstringType value="2"/>
<FontMatrix value="0.001 0 0 0.001 0 0"/>
<FontBBox value="33 -87 992 855"/>
<StrokeWidth value="0"/>
<!-- charset is dumped separately as the 'GlyphOrder' element -->
<Encoding name="StandardEncoding"/>
<Private>
<BlueValues value="0 0"/>
<BlueScale value="0.039625"/>
<BlueShift value="7"/>
<BlueFuzz value="1"/>
<ForceBold value="0"/>
<LanguageGroup value="0"/>
<ExpansionFactor value="0.06"/>
<initialRandomSeed value="0"/>
<defaultWidthX value="1000"/>
<nominalWidthX value="705"/>
</Private>
<CharStrings>
<CharString name=".notdef">
-455 endchar
</CharString>
<CharString name="uni3001">
245 -76 rmoveto
129 111 rlineto
-44 56 -100 103 -70 58 rrcurveto
-127 -109 rlineto
69 -61 84 -86 59 -72 rrcurveto
endchar
</CharString>
<CharString name="uni3073">
729 763 rmoveto
-152 -42 rlineto
75 -225 86 -176 109 -123 rrcurveto
97 140 rlineto
-155 146 -41 152 -19 128 rrcurveto
-677 -48 rmoveto
11 -156 rlineto
24 5 15 2 22 3 rrcurveto
26 3 53 6 31 1 rrcurveto
-96 -130 -50 -109 0 -149 rrcurveto
0 -190 149 -88 163 0 rrcurveto
344 0 43 303 -58 260 rrcurveto
-142 223 rlineto
96 -376 -59 -246 -221 0 rrcurveto
-92 0 -67 46 0 103 rrcurveto
0 184 125 143 71 54 rrcurveto
16 10 18 8 15 6 rrcurveto
-46 134 rlineto
-69 -25 -166 -20 -98 -5 rrcurveto
-19 -1 -20 0 -19 1 rrcurveto
768 103 rmoveto
-88 -27 rlineto
22 -45 16 -54 15 -49 rrcurveto
87 28 rlineto
-11 41 -23 62 -18 44 rrcurveto
110 37 rmoveto
-85 -28 rlineto
21 -44 19 -57 14 -46 rrcurveto
88 28 rlineto
-13 40 -22 63 -22 44 rrcurveto
endchar
</CharString>
<CharString name="uni3074">
729 763 rmoveto
-152 -42 rlineto
75 -225 86 -176 109 -123 rrcurveto
97 140 rlineto
-155 146 -41 152 -19 128 rrcurveto
-677 -48 rmoveto
11 -156 rlineto
24 5 15 2 22 3 rrcurveto
26 3 53 6 31 1 rrcurveto
-96 -130 -50 -109 0 -149 rrcurveto
0 -190 149 -88 163 0 rrcurveto
344 0 43 303 -58 260 rrcurveto
-142 223 rlineto
96 -376 -59 -246 -221 0 rrcurveto
-92 0 -67 46 0 103 rrcurveto
0 184 125 143 71 54 rrcurveto
16 10 18 8 15 6 rrcurveto
-46 134 rlineto
-69 -25 -166 -20 -98 -5 rrcurveto
-19 -1 -20 0 -19 1 rrcurveto
772 16 rmoveto
0 27 22 22 27 0 rrcurveto
27 0 22 -22 0 -27 rrcurveto
0 -27 -22 -22 -27 0 rrcurveto
-27 0 -22 22 0 27 rrcurveto
-70 0 rmoveto
0 -66 53 -53 66 0 rrcurveto
66 0 53 53 0 66 rrcurveto
0 66 -53 53 -66 0 rrcurveto
-66 0 -53 -53 0 -66 rrcurveto
endchar
</CharString>
<CharString name="uni307B">
758 687 rmoveto
-141 0 rlineto
0 -42 0 -111 0 -88 rrcurveto
0 -104 8 -126 0 -63 rrcurveto
0 -45 -23 -24 -49 0 rrcurveto
-37 0 -24 16 0 29 rrcurveto
0 28 23 18 48 0 rrcurveto
107 0 121 -81 97 -98 rrcurveto
79 131 rlineto
-51 45 -135 115 -213 0 rrcurveto
-137 0 -76 -72 0 -97 rrcurveto
0 -116 100 -52 119 0 rrcurveto
142 0 55 65 0 93 rrcurveto
0 97 -13 99 0 147 rrcurveto
0 64 0 96 0 76 rrcurveto
-360 -167 rmoveto
1 -139 rlineto
195 -9 191 7 133 16 rrcurveto
0 139 rlineto
-148 -18 -178 -11 -194 15 rrcurveto
15 235 rmoveto
0 -134 rlineto
197 -9 162 8 126 14 rrcurveto
0 134 rlineto
-127 -19 -163 -9 -195 15 rrcurveto
-117 26 rmoveto
-168 14 rlineto
-1 -37 -6 -47 -4 -29 rrcurveto
-11 -74 -26 -192 0 -153 rrcurveto
0 -136 20 -117 21 -68 rrcurveto
139 10 rlineto
-1 16 0 18 0 11 rrcurveto
0 10 3 23 3 14 rrcurveto
12 58 30 101 30 90 rrcurveto
-73 59 rlineto
-13 -30 -14 -23 -12 -29 rrcurveto
-1 4 0 20 0 3 rrcurveto
0 93 33 237 12 52 rrcurveto
4 18 14 62 9 22 rrcurveto
endchar
</CharString>
<CharString name="uni30FB">
500 520 rmoveto
-77 0 -63 -63 0 -77 rrcurveto
0 -77 63 -63 77 0 rrcurveto
77 0 63 63 0 77 rrcurveto
0 77 -63 63 -77 0 rrcurveto
endchar
</CharString>
<CharString name="uniFF1A">
500 500 rmoveto
60 0 46 46 0 58 rrcurveto
0 60 -46 46 -60 0 rrcurveto
-60 0 -46 -46 0 -60 rrcurveto
0 -58 46 -46 60 0 rrcurveto
0 -470 rmoveto
60 0 46 46 0 58 rrcurveto
0 60 -46 46 -60 0 rrcurveto
-60 0 -46 -46 0 -60 rrcurveto
0 -58 46 -46 60 0 rrcurveto
endchar
</CharString>
<CharString name="uniFF2D">
113 0 rmoveto
160 0 rlineto
0 255 rlineto
0 75 -12 113 -9 74 rrcurveto
4 0 rlineto
72 -182 rlineto
121 -272 rlineto
98 0 rlineto
120 272 rlineto
73 182 rlineto
5 0 rlineto
-10 -74 -12 -113 0 -75 rrcurveto
0 -255 rlineto
163 0 rlineto
0 748 rlineto
-194 0 rlineto
-135 -325 rlineto
-17 -43 -18 -47 -18 -46 rrcurveto
-5 0 rlineto
-16 46 -19 47 -16 43 rrcurveto
-142 325 rlineto
-193 0 rlineto
0 -748 rlineto
endchar
</CharString>
</CharStrings>
</CFFFont>
<GlobalSubrs>
<!-- The 'index' attribute is only for humans; it is ignored when parsed. -->
</GlobalSubrs>
</CFF>
<GPOS>
<Version value="0x00010000"/>
<ScriptList>
<!-- ScriptCount=1 -->
<ScriptRecord index="0">
<ScriptTag value="DFLT"/>
<Script>
<DefaultLangSys>
<ReqFeatureIndex value="65535"/>
<!-- FeatureCount=1 -->
<FeatureIndex index="0" value="0"/>
</DefaultLangSys>
<!-- LangSysCount=0 -->
</Script>
</ScriptRecord>
</ScriptList>
<FeatureList>
<!-- FeatureCount=1 -->
<FeatureRecord index="0">
<FeatureTag value="vpal"/>
<Feature>
<!-- LookupCount=1 -->
<LookupListIndex index="0" value="0"/>
</Feature>
</FeatureRecord>
</FeatureList>
<LookupList>
<!-- LookupCount=1 -->
<Lookup index="0">
<LookupType value="1"/>
<LookupFlag value="0"/>
<!-- SubTableCount=3 -->
<SinglePos index="0" Format="2">
<Coverage Format="1">
<Glyph value="uni3001"/>
<Glyph value="uni30FB"/>
<Glyph value="uniFF1A"/>
</Coverage>
<ValueFormat value="5"/>
<!-- ValueCount=3 -->
<Value index="0" XPlacement="-3" XAdvance="-500"/>
<Value index="1" XPlacement="-250" XAdvance="-500"/>
<Value index="2" XPlacement="-250" XAdvance="-500"/>
</SinglePos>
<SinglePos index="1" Format="2">
<Coverage Format="1">
<Glyph value="uni3073"/>
<Glyph value="uni3074"/>
</Coverage>
<ValueFormat value="4"/>
<!-- ValueCount=2 -->
<Value index="0" XAdvance="-35"/>
<Value index="1" XAdvance="-30"/>
</SinglePos>
<SinglePos index="2" Format="2">
<Coverage Format="1">
<Glyph value="uniFF2D"/>
<Glyph value="uni307B"/>
</Coverage>
<ValueFormat value="1"/>
<!-- ValueCount=2 -->
<Value index="0" XPlacement="1"/>
<Value index="1" XPlacement="10"/>
</SinglePos>
</Lookup>
</LookupList>
</GPOS>
<hmtx>
<mtx name=".notdef" width="250" lsb="0"/>
<mtx name="uni3001" width="1000" lsb="33"/>
<mtx name="uni3073" width="1000" lsb="52"/>
<mtx name="uni3074" width="1000" lsb="52"/>
<mtx name="uni307B" width="1000" lsb="80"/>
<mtx name="uni30FB" width="1000" lsb="360"/>
<mtx name="uniFF1A" width="1000" lsb="394"/>
<mtx name="uniFF2D" width="1000" lsb="113"/>
</hmtx>
</ttFont>

View File

@ -1,5 +1,5 @@
<?xml version="1.0" encoding="UTF-8"?> <?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="OTTO" ttLibVersion="3.38"> <ttFont sfntVersion="OTTO" ttLibVersion="3.42">
<fvar> <fvar>
@ -67,29 +67,29 @@
<BlueValues> <BlueValues>
<blend value="-12 0 0"/> <blend value="-12 0 0"/>
<blend value="0 0 0"/> <blend value="0 0 0"/>
<blend value="486 -8 -8"/> <blend value="486 -8 14"/>
<blend value="498 0 0"/> <blend value="498 0 0"/>
<blend value="574 4 4"/> <blend value="574 4 -8"/>
<blend value="586 0 0"/> <blend value="586 0 0"/>
<blend value="638 6 6"/> <blend value="638 6 -10"/>
<blend value="650 0 0"/> <blend value="650 0 0"/>
<blend value="656 2 2"/> <blend value="656 2 -2"/>
<blend value="668 0 0"/> <blend value="668 0 0"/>
<blend value="712 6 6"/> <blend value="712 6 -10"/>
<blend value="724 0 0"/> <blend value="724 0 0"/>
</BlueValues> </BlueValues>
<OtherBlues> <OtherBlues>
<blend value="-217 -17 -17"/> <blend value="-217 -17 29"/>
<blend value="-205 0 0"/> <blend value="-205 0 0"/>
</OtherBlues> </OtherBlues>
<BlueScale value="0.0625"/> <BlueScale value="0.0625"/>
<BlueShift value="7"/> <BlueShift value="7"/>
<BlueFuzz value="0"/> <BlueFuzz value="0"/>
<StdHW> <StdHW>
<blend value="67 -39.0 -39.0"/> <blend value="67 -39.0 67.0"/>
</StdHW> </StdHW>
<StdVW> <StdVW>
<blend value="85 -51.0 -51.0"/> <blend value="85 -51.0 87.0"/>
</StdVW> </StdVW>
</Private> </Private>
</FontDict> </FontDict>

View File

@ -0,0 +1,76 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="OTTO" ttLibVersion="3.42">
<CFF2>
<major value="2"/>
<minor value="0"/>
<CFFFont name="CFF2Font">
<FontMatrix value="0.001 0 0 0.001 0 0"/>
<FDArray>
<FontDict index="0">
<Private>
<BlueValues>
<blend value="-12 0"/>
<blend value="0 0"/>
<blend value="478 8"/>
<blend value="490 0"/>
<blend value="570 -4"/>
<blend value="582 0"/>
<blend value="640 -6"/>
<blend value="652 0"/>
<blend value="660 -2"/>
<blend value="672 0"/>
<blend value="722 -6"/>
<blend value="734 0"/>
</BlueValues>
<OtherBlues>
<blend value="-234 17"/>
<blend value="-222 0"/>
</OtherBlues>
<BlueScale value="0.0625"/>
<BlueShift value="7"/>
<BlueFuzz value="0"/>
<StdHW>
<blend value="28 39.0"/>
</StdHW>
<StdVW>
<blend value="34 51.0"/>
</StdVW>
</Private>
</FontDict>
</FDArray>
<CharStrings>
<CharString name=".notdef">
</CharString>
<CharString name="A">
</CharString>
</CharStrings>
<VarStore Format="1">
<Format value="1"/>
<VarRegionList>
<!-- RegionAxisCount=1 -->
<!-- RegionCount=1 -->
<Region index="0">
<VarRegionAxis index="0">
<StartCoord value="0.0"/>
<PeakCoord value="1.0"/>
<EndCoord value="1.0"/>
</VarRegionAxis>
</Region>
</VarRegionList>
<!-- VarDataCount=1 -->
<VarData index="0">
<!-- ItemCount=0 -->
<NumShorts value="0"/>
<!-- VarRegionCount=1 -->
<VarRegionIndex index="0" value="0"/>
</VarData>
</VarStore>
</CFFFont>
<GlobalSubrs>
<!-- The 'index' attribute is only for humans; it is ignored when parsed. -->
</GlobalSubrs>
</CFF2>
</ttFont>

View File

@ -0,0 +1,120 @@
<?xml version="1.0" encoding="UTF-8"?>
<ttFont sfntVersion="OTTO" ttLibVersion="3.42">
<GPOS>
<Version value="0x00010000"/>
<ScriptList>
<!-- ScriptCount=1 -->
<ScriptRecord index="0">
<ScriptTag value="DFLT"/>
<Script>
<DefaultLangSys>
<ReqFeatureIndex value="65535"/>
<!-- FeatureCount=1 -->
<FeatureIndex index="0" value="0"/>
</DefaultLangSys>
<!-- LangSysCount=0 -->
</Script>
</ScriptRecord>
</ScriptList>
<FeatureList>
<!-- FeatureCount=1 -->
<FeatureRecord index="0">
<FeatureTag value="vpal"/>
<Feature>
<!-- LookupCount=1 -->
<LookupListIndex index="0" value="0"/>
</Feature>
</FeatureRecord>
</FeatureList>
<LookupList>
<!-- LookupCount=1 -->
<Lookup index="0">
<LookupType value="1"/>
<LookupFlag value="0"/>
<!-- SubTableCount=6 -->
<SinglePos index="0" Format="2">
<Coverage Format="1">
<Glyph value="uniFF1A"/>
<Glyph value="uni3074"/>
</Coverage>
<ValueFormat value="7"/>
<!-- ValueCount=2 -->
<Value index="0" XPlacement="-250" YPlacement="0" XAdvance="-500"/>
<Value index="1" XPlacement="0" YPlacement="0" XAdvance="-30"/>
</SinglePos>
<SinglePos index="1" Format="1">
<Coverage Format="1">
<Glyph value="uni3001"/>
</Coverage>
<ValueFormat value="23"/>
<Value XPlacement="-9" YPlacement="0" XAdvance="-500">
<XPlaDevice>
<StartSize value="0"/>
<EndSize value="4"/>
<DeltaFormat value="32768"/>
</XPlaDevice>
</Value>
</SinglePos>
<SinglePos index="2" Format="1">
<Coverage Format="1">
<Glyph value="uni30FB"/>
</Coverage>
<ValueFormat value="39"/>
<Value XPlacement="-250" YPlacement="1" XAdvance="-500">
<YPlaDevice>
<StartSize value="0"/>
<EndSize value="2"/>
<DeltaFormat value="32768"/>
</YPlaDevice>
</Value>
</SinglePos>
<SinglePos index="3" Format="1">
<Coverage Format="1">
<Glyph value="uniFF2D"/>
</Coverage>
<ValueFormat value="87"/>
<Value XPlacement="12" YPlacement="0" XAdvance="23">
<XPlaDevice>
<StartSize value="0"/>
<EndSize value="1"/>
<DeltaFormat value="32768"/>
</XPlaDevice>
<XAdvDevice>
<StartSize value="0"/>
<EndSize value="0"/>
<DeltaFormat value="32768"/>
</XAdvDevice>
</Value>
</SinglePos>
<SinglePos index="4" Format="1">
<Coverage Format="1">
<Glyph value="uni3073"/>
</Coverage>
<ValueFormat value="71"/>
<Value XPlacement="0" YPlacement="0" XAdvance="-36">
<XAdvDevice>
<StartSize value="0"/>
<EndSize value="3"/>
<DeltaFormat value="32768"/>
</XAdvDevice>
</Value>
</SinglePos>
<SinglePos index="5" Format="1">
<Coverage Format="1">
<Glyph value="uni307B"/>
</Coverage>
<ValueFormat value="23"/>
<Value XPlacement="11" YPlacement="0" XAdvance="0">
<XPlaDevice>
<StartSize value="0"/>
<EndSize value="2"/>
<DeltaFormat value="32768"/>
</XPlaDevice>
</Value>
</SinglePos>
</Lookup>
</LookupList>
</GPOS>
</ttFont>

View File

@ -0,0 +1,35 @@
<?xml version='1.0' encoding='utf-8'?>
<designspace format="3">
<axes>
<axis default="0" maximum="1000" minimum="0" name="weight" tag="wght" />
</axes>
<sources>
<source filename="master_vpal_test/master_vpal_test_0.ufo" stylename="w0.00">
<info copy="1" />
<location>
<dimension name="weight" xvalue="0.00" />
</location>
</source>
<source filename="master_vpal_test/master_vpal_test_1.ufo" stylename="w1000.00">
<location>
<dimension name="weight" xvalue="1000.00" />
</location>
</source>
</sources>
<instances>
<instance familyname="SHSansJPVFTest" filename="instances/SHSansJPVFTest-ExtraLight.otf" postscriptfontname="SHSansJPVFTest-ExtraLight" stylename="ExtraLight">
<location>
<dimension name="weight" xvalue="0" />
</location>
<kerning />
<info />
</instance>
<instance familyname="SHSansJPVFTest" filename="instances/SHSansJPVFTest-Heavy.otf" postscriptfontname="SHSansJPVFTest-Heavy" stylename="Heavy">
<location>
<dimension name="weight" xvalue="1000" />
</location>
<kerning />
<info />
</instance>
</instances>
</designspace>

View File

@ -2,6 +2,7 @@ from __future__ import print_function, division, absolute_import
from fontTools.misc.py23 import * from fontTools.misc.py23 import *
from fontTools.ttLib import TTFont, newTable from fontTools.ttLib import TTFont, newTable
from fontTools.varLib import build from fontTools.varLib import build
from fontTools.varLib.mutator import instantiateVariableFont
from fontTools.varLib import main as varLib_main, load_masters from fontTools.varLib import main as varLib_main, load_masters
from fontTools.designspaceLib import ( from fontTools.designspaceLib import (
DesignSpaceDocumentError, DesignSpaceDocument, SourceDescriptor, DesignSpaceDocumentError, DesignSpaceDocument, SourceDescriptor,
@ -227,6 +228,28 @@ class BuildTest(unittest.TestCase):
expected_ttx_name=test_name expected_ttx_name=test_name
) )
def test_varlib_nonmarking_CFF2(self):
ds_path = self.get_test_input('TestNonMarkingCFF2.designspace')
ttx_dir = self.get_test_input("master_non_marking_cff2")
expected_ttx_path = self.get_test_output("TestNonMarkingCFF2.ttx")
self.temp_dir()
for path in self.get_file_list(ttx_dir, '.ttx', 'TestNonMarkingCFF2_'):
self.compile_font(path, ".otf", self.tempdir)
ds = DesignSpaceDocument.fromfile(ds_path)
for source in ds.sources:
source.path = os.path.join(
self.tempdir, os.path.basename(source.filename).replace(".ufo", ".otf")
)
ds.updatePaths()
varfont, _, _ = build(ds)
varfont = reload_font(varfont)
tables = ["CFF2"]
self.expect_ttx(varfont, expected_ttx_path, tables)
def test_varlib_build_CFF2(self): def test_varlib_build_CFF2(self):
ds_path = self.get_test_input('TestCFF2.designspace') ds_path = self.get_test_input('TestCFF2.designspace')
ttx_dir = self.get_test_input("master_cff2") ttx_dir = self.get_test_input("master_cff2")
@ -249,7 +272,6 @@ class BuildTest(unittest.TestCase):
tables = ["fvar", "CFF2"] tables = ["fvar", "CFF2"]
self.expect_ttx(varfont, expected_ttx_path, tables) self.expect_ttx(varfont, expected_ttx_path, tables)
def test_varlib_build_sparse_CFF2(self): def test_varlib_build_sparse_CFF2(self):
ds_path = self.get_test_input('TestSparseCFF2VF.designspace') ds_path = self.get_test_input('TestSparseCFF2VF.designspace')
ttx_dir = self.get_test_input("master_sparse_cff2") ttx_dir = self.get_test_input("master_sparse_cff2")
@ -272,6 +294,27 @@ class BuildTest(unittest.TestCase):
tables = ["fvar", "CFF2"] tables = ["fvar", "CFF2"]
self.expect_ttx(varfont, expected_ttx_path, tables) self.expect_ttx(varfont, expected_ttx_path, tables)
def test_varlib_build_vpal(self):
ds_path = self.get_test_input('test_vpal.designspace')
ttx_dir = self.get_test_input("master_vpal_test")
expected_ttx_path = self.get_test_output("test_vpal.ttx")
self.temp_dir()
for path in self.get_file_list(ttx_dir, '.ttx', 'master_vpal_test_'):
self.compile_font(path, ".otf", self.tempdir)
ds = DesignSpaceDocument.fromfile(ds_path)
for source in ds.sources:
source.path = os.path.join(
self.tempdir, os.path.basename(source.filename).replace(".ufo", ".otf")
)
ds.updatePaths()
varfont, _, _ = build(ds)
varfont = reload_font(varfont)
tables = ["GPOS"]
self.expect_ttx(varfont, expected_ttx_path, tables)
def test_varlib_main_ttf(self): def test_varlib_main_ttf(self):
"""Mostly for testing varLib.main() """Mostly for testing varLib.main()
@ -496,6 +539,98 @@ class BuildTest(unittest.TestCase):
self.expect_ttx(varfont, expected_ttx_path, tables) self.expect_ttx(varfont, expected_ttx_path, tables)
self.check_ttx_dump(varfont, expected_ttx_path, tables, suffix) self.check_ttx_dump(varfont, expected_ttx_path, tables, suffix)
def test_kerning_merging(self):
"""Test the correct merging of class-based pair kerning.
Problem description at https://github.com/fonttools/fonttools/pull/1638.
Test font and Designspace generated by
https://gist.github.com/madig/183d0440c9f7d05f04bd1280b9664bd1.
"""
ds_path = self.get_test_input("KerningMerging.designspace")
ttx_dir = self.get_test_input("master_kerning_merging")
ds = DesignSpaceDocument.fromfile(ds_path)
for source in ds.sources:
ttx_dump = TTFont()
ttx_dump.importXML(
os.path.join(
ttx_dir, os.path.basename(source.filename).replace(".ttf", ".ttx")
)
)
source.font = reload_font(ttx_dump)
varfont, _, _ = build(ds)
varfont = reload_font(varfont)
class_kerning_tables = [
t
for l in varfont["GPOS"].table.LookupList.Lookup
for t in l.SubTable
if t.Format == 2
]
assert len(class_kerning_tables) == 1
class_kerning_table = class_kerning_tables[0]
# Test that no class kerned against class zero (containing all glyphs not
# classed) has a `XAdvDevice` table attached, which in the variable font
# context is a "VariationIndex" table and points to kerning deltas in the GDEF
# table. Variation deltas of any kerning class against class zero should
# probably never exist.
for class1_record in class_kerning_table.Class1Record:
class2_zero = class1_record.Class2Record[0]
assert getattr(class2_zero.Value1, "XAdvDevice", None) is None
# Assert the variable font's kerning table (without deltas) is equal to the
# default font's kerning table. The bug fixed in
# https://github.com/fonttools/fonttools/pull/1638 caused rogue kerning
# values to be written to the variable font.
assert _extract_flat_kerning(varfont, class_kerning_table) == {
("A", ".notdef"): 0,
("A", "A"): 0,
("A", "B"): -20,
("A", "C"): 0,
("A", "D"): -20,
("B", ".notdef"): 0,
("B", "A"): 0,
("B", "B"): 0,
("B", "C"): 0,
("B", "D"): 0,
}
instance_thin = instantiateVariableFont(varfont, {"wght": 100})
instance_thin_kerning_table = (
instance_thin["GPOS"].table.LookupList.Lookup[0].SubTable[0]
)
assert _extract_flat_kerning(instance_thin, instance_thin_kerning_table) == {
("A", ".notdef"): 0,
("A", "A"): 0,
("A", "B"): 0,
("A", "C"): 10,
("A", "D"): 0,
("B", ".notdef"): 0,
("B", "A"): 0,
("B", "B"): 0,
("B", "C"): 10,
("B", "D"): 0,
}
instance_black = instantiateVariableFont(varfont, {"wght": 900})
instance_black_kerning_table = (
instance_black["GPOS"].table.LookupList.Lookup[0].SubTable[0]
)
assert _extract_flat_kerning(instance_black, instance_black_kerning_table) == {
("A", ".notdef"): 0,
("A", "A"): 0,
("A", "B"): 0,
("A", "C"): 0,
("A", "D"): 40,
("B", ".notdef"): 0,
("B", "A"): 0,
("B", "B"): 0,
("B", "C"): 0,
("B", "D"): 40,
}
def test_load_masters_layerName_without_required_font(): def test_load_masters_layerName_without_required_font():
ds = DesignSpaceDocument() ds = DesignSpaceDocument()
@ -511,5 +646,20 @@ def test_load_masters_layerName_without_required_font():
load_masters(ds) load_masters(ds)
def _extract_flat_kerning(font, pairpos_table):
extracted_kerning = {}
for glyph_name_1 in pairpos_table.Coverage.glyphs:
class_def_1 = pairpos_table.ClassDef1.classDefs.get(glyph_name_1, 0)
for glyph_name_2 in font.getGlyphOrder():
class_def_2 = pairpos_table.ClassDef2.classDefs.get(glyph_name_2, 0)
kern_value = (
pairpos_table.Class1Record[class_def_1]
.Class2Record[class_def_2]
.Value1.XAdvance
)
extracted_kerning[(glyph_name_1, glyph_name_2)] = kern_value
return extracted_kerning
if __name__ == "__main__": if __name__ == "__main__":
sys.exit(unittest.main()) sys.exit(unittest.main())

View File

@ -8,4 +8,4 @@ scipy==1.3.0; platform_python_implementation != "PyPy" and python_version >= '3.
munkres==1.0.12; platform_python_implementation == "PyPy" and python_version < '3.5' # pyup: ignore munkres==1.0.12; platform_python_implementation == "PyPy" and python_version < '3.5' # pyup: ignore
munkres==1.1.2; platform_python_implementation == "PyPy" and python_version >= '3.5' munkres==1.1.2; platform_python_implementation == "PyPy" and python_version >= '3.5'
zopfli==0.1.6 zopfli==0.1.6
fs==2.4.5 fs==2.4.8

View File

@ -1,5 +1,5 @@
[bumpversion] [bumpversion]
current_version = 3.42.1.dev0 current_version = 3.43.1.dev0
commit = True commit = True
tag = False tag = False
tag_name = {new_version} tag_name = {new_version}

View File

@ -352,7 +352,7 @@ def find_data_files(manpath="share/man"):
setup( setup(
name="fonttools", name="fonttools",
version="3.42.1.dev0", version="3.43.1.dev0",
description="Tools to manipulate font files", description="Tools to manipulate font files",
author="Just van Rossum", author="Just van Rossum",
author_email="just@letterror.com", author_email="just@letterror.com",