2016-10-14 17:13:56 +02:00
|
|
|
from fontTools.misc.testTools import FakeFont, getXML, parseXML
|
|
|
|
from fontTools.misc.textTools import deHexStr
|
2016-12-21 09:53:32 +00:00
|
|
|
from fontTools.ttLib import newTable
|
2016-10-14 17:13:56 +02:00
|
|
|
import unittest
|
|
|
|
|
|
|
|
|
|
|
|
STAT_DATA = deHexStr(
|
|
|
|
"0001 0000 " # 0: Version=1.0
|
|
|
|
"0008 0002 " # 4: DesignAxisSize=8, DesignAxisCount=2
|
|
|
|
"0000 0012 " # 8: OffsetToDesignAxes=18
|
|
|
|
"0003 0000 0022 " # 12: AxisValueCount=3, OffsetToAxisValueOffsets=34
|
|
|
|
"7767 6874 " # 18: DesignAxis[0].AxisTag='wght'
|
|
|
|
"012D 0002 " # 22: DesignAxis[0].NameID=301, .AxisOrdering=2
|
|
|
|
"5445 5354 " # 26: DesignAxis[1].AxisTag='TEST'
|
|
|
|
"012E 0001 " # 30: DesignAxis[1].NameID=302, .AxisOrdering=1
|
2016-12-02 15:26:49 -08:00
|
|
|
"0006 0012 0026 " # 34: AxisValueOffsets = [6, 18, 38] (+34)
|
2016-10-14 17:13:56 +02:00
|
|
|
"0001 0000 0000 " # 40: AxisValue[0].Format=1, .AxisIndex=0, .Flags=0
|
|
|
|
"0191 0190 0000 " # 46: AxisValue[0].ValueNameID=401, .Value=400.0
|
|
|
|
"0002 0001 0000 " # 52: AxisValue[1].Format=2, .AxisIndex=1, .Flags=0
|
|
|
|
"0192 " # 58: AxisValue[1].ValueNameID=402
|
|
|
|
"0002 0000 " # 60: AxisValue[1].NominalValue=2.0
|
|
|
|
"0001 0000 " # 64: AxisValue[1].RangeMinValue=1.0
|
|
|
|
"0003 0000 " # 68: AxisValue[1].RangeMaxValue=3.0
|
|
|
|
"0003 0000 0000 " # 72: AxisValue[2].Format=3, .AxisIndex=0, .Flags=0
|
2016-12-02 15:26:49 -08:00
|
|
|
"0002 " # 78: AxisValue[2].ValueNameID=2 'Regular'
|
|
|
|
"0190 0000 02BC 0000 " # 80: AxisValue[2].Value=400.0, .LinkedValue=700.0
|
|
|
|
) # 88: <end>
|
|
|
|
assert len(STAT_DATA) == 88
|
2016-10-14 17:13:56 +02:00
|
|
|
|
|
|
|
|
2016-12-21 13:24:51 +00:00
|
|
|
STAT_XML = [
|
|
|
|
'<Version value="0x00010000"/>',
|
|
|
|
'<DesignAxisRecordSize value="8"/>',
|
|
|
|
"<!-- DesignAxisCount=2 -->",
|
|
|
|
"<DesignAxisRecord>",
|
|
|
|
' <Axis index="0">',
|
|
|
|
' <AxisTag value="wght"/>',
|
|
|
|
' <AxisNameID value="301"/>',
|
|
|
|
' <AxisOrdering value="2"/>',
|
|
|
|
" </Axis>",
|
|
|
|
' <Axis index="1">',
|
|
|
|
' <AxisTag value="TEST"/>',
|
|
|
|
' <AxisNameID value="302"/>',
|
|
|
|
' <AxisOrdering value="1"/>',
|
|
|
|
" </Axis>",
|
|
|
|
"</DesignAxisRecord>",
|
|
|
|
"<!-- AxisValueCount=3 -->",
|
|
|
|
"<AxisValueArray>",
|
|
|
|
' <AxisValue index="0" Format="1">',
|
|
|
|
' <AxisIndex value="0"/>',
|
|
|
|
' <Flags value="0"/>',
|
|
|
|
' <ValueNameID value="401"/>',
|
|
|
|
' <Value value="400.0"/>',
|
|
|
|
" </AxisValue>",
|
|
|
|
' <AxisValue index="1" Format="2">',
|
|
|
|
' <AxisIndex value="1"/>',
|
|
|
|
' <Flags value="0"/>',
|
|
|
|
' <ValueNameID value="402"/>',
|
|
|
|
' <NominalValue value="2.0"/>',
|
|
|
|
' <RangeMinValue value="1.0"/>',
|
|
|
|
' <RangeMaxValue value="3.0"/>',
|
|
|
|
" </AxisValue>",
|
|
|
|
' <AxisValue index="2" Format="3">',
|
|
|
|
' <AxisIndex value="0"/>',
|
|
|
|
' <Flags value="0"/>',
|
|
|
|
' <ValueNameID value="2"/>',
|
|
|
|
' <Value value="400.0"/>',
|
|
|
|
' <LinkedValue value="700.0"/>',
|
|
|
|
" </AxisValue>",
|
|
|
|
"</AxisValueArray>",
|
|
|
|
]
|
2016-10-14 17:13:56 +02:00
|
|
|
|
|
|
|
|
2016-12-02 19:12:26 -08:00
|
|
|
# Contains junk data for making sure we get our offset decoding right.
|
|
|
|
STAT_DATA_WITH_AXIS_JUNK = deHexStr(
|
|
|
|
"0001 0000 " # 0: Version=1.0
|
|
|
|
"000A 0002 " # 4: DesignAxisSize=10, DesignAxisCount=2
|
|
|
|
"0000 0012 " # 8: OffsetToDesignAxes=18
|
|
|
|
"0000 0000 0000 " # 12: AxisValueCount=3, OffsetToAxisValueOffsets=34
|
|
|
|
"7767 6874 " # 18: DesignAxis[0].AxisTag='wght'
|
|
|
|
"012D 0002 " # 22: DesignAxis[0].NameID=301, .AxisOrdering=2
|
|
|
|
"DEAD " # 26: <junk>
|
|
|
|
"5445 5354 " # 28: DesignAxis[1].AxisTag='TEST'
|
|
|
|
"012E 0001 " # 32: DesignAxis[1].NameID=302, .AxisOrdering=1
|
|
|
|
"BEEF " # 36: <junk>
|
|
|
|
) # 38: <end>
|
|
|
|
|
|
|
|
assert len(STAT_DATA_WITH_AXIS_JUNK) == 38
|
|
|
|
|
|
|
|
|
2016-12-21 13:24:51 +00:00
|
|
|
STAT_XML_WITH_AXIS_JUNK = [
|
|
|
|
'<Version value="0x00010000"/>',
|
|
|
|
'<DesignAxisRecordSize value="10"/>',
|
|
|
|
"<!-- DesignAxisCount=2 -->",
|
|
|
|
"<DesignAxisRecord>",
|
|
|
|
' <Axis index="0">',
|
|
|
|
' <AxisTag value="wght"/>',
|
|
|
|
' <AxisNameID value="301"/>',
|
|
|
|
' <AxisOrdering value="2"/>',
|
|
|
|
' <MoreBytes index="0" value="222"/>', # 0xDE
|
|
|
|
' <MoreBytes index="1" value="173"/>', # 0xAD
|
|
|
|
" </Axis>",
|
|
|
|
' <Axis index="1">',
|
|
|
|
' <AxisTag value="TEST"/>',
|
|
|
|
' <AxisNameID value="302"/>',
|
|
|
|
' <AxisOrdering value="1"/>',
|
|
|
|
' <MoreBytes index="0" value="190"/>', # 0xBE
|
|
|
|
' <MoreBytes index="1" value="239"/>', # 0xEF
|
|
|
|
" </Axis>",
|
|
|
|
"</DesignAxisRecord>",
|
|
|
|
"<!-- AxisValueCount=0 -->",
|
|
|
|
]
|
2016-12-02 19:12:26 -08:00
|
|
|
|
|
|
|
|
2016-10-14 17:13:56 +02:00
|
|
|
STAT_DATA_AXIS_VALUE_FORMAT3 = deHexStr(
|
|
|
|
"0001 0000 " # 0: Version=1.0
|
|
|
|
"0008 0001 " # 4: DesignAxisSize=8, DesignAxisCount=1
|
|
|
|
"0000 0012 " # 8: OffsetToDesignAxes=18
|
|
|
|
"0001 " # 12: AxisValueCount=1
|
|
|
|
"0000 001A " # 14: OffsetToAxisValueOffsets=26
|
|
|
|
"7767 6874 " # 18: DesignAxis[0].AxisTag='wght'
|
|
|
|
"0102 " # 22: DesignAxis[0].AxisNameID=258 'Weight'
|
|
|
|
"0000 " # 24: DesignAxis[0].AxisOrdering=0
|
|
|
|
"0002 " # 26: AxisValueOffsets=[2] (+26)
|
|
|
|
"0003 " # 28: AxisValue[0].Format=3
|
|
|
|
"0000 0002 " # 30: AxisValue[0].AxisIndex=0, .Flags=0x2
|
|
|
|
"0002 " # 34: AxisValue[0].ValueNameID=2 'Regular'
|
|
|
|
"0190 0000 " # 36: AxisValue[0].Value=400.0
|
|
|
|
"02BC 0000 " # 40: AxisValue[0].LinkedValue=700.0
|
|
|
|
) # 44: <end>
|
|
|
|
assert len(STAT_DATA_AXIS_VALUE_FORMAT3) == 44
|
|
|
|
|
|
|
|
|
2016-12-21 13:24:51 +00:00
|
|
|
STAT_XML_AXIS_VALUE_FORMAT3 = [
|
|
|
|
'<Version value="0x00010000"/>',
|
|
|
|
'<DesignAxisRecordSize value="8"/>',
|
|
|
|
"<!-- DesignAxisCount=1 -->",
|
|
|
|
"<DesignAxisRecord>",
|
|
|
|
' <Axis index="0">',
|
|
|
|
' <AxisTag value="wght"/>',
|
|
|
|
' <AxisNameID value="258"/>',
|
|
|
|
' <AxisOrdering value="0"/>',
|
|
|
|
" </Axis>",
|
|
|
|
"</DesignAxisRecord>",
|
|
|
|
"<!-- AxisValueCount=1 -->",
|
|
|
|
"<AxisValueArray>",
|
|
|
|
' <AxisValue index="0" Format="3">',
|
|
|
|
' <AxisIndex value="0"/>',
|
2020-08-11 21:21:30 -07:00
|
|
|
' <Flags value="2"/> <!-- ElidableAxisValueName -->',
|
2016-12-21 13:24:51 +00:00
|
|
|
' <ValueNameID value="2"/>',
|
|
|
|
' <Value value="400.0"/>',
|
|
|
|
' <LinkedValue value="700.0"/>',
|
|
|
|
" </AxisValue>",
|
|
|
|
"</AxisValueArray>",
|
|
|
|
]
|
2016-10-14 17:13:56 +02:00
|
|
|
|
|
|
|
|
2016-12-13 09:44:03 +01:00
|
|
|
STAT_DATA_VERSION_1_1 = deHexStr(
|
|
|
|
"0001 0001 " # 0: Version=1.1
|
|
|
|
"0008 0001 " # 4: DesignAxisSize=8, DesignAxisCount=1
|
|
|
|
"0000 0014 " # 8: OffsetToDesignAxes=20
|
|
|
|
"0001 " # 12: AxisValueCount=1
|
|
|
|
"0000 001C " # 14: OffsetToAxisValueOffsets=28
|
|
|
|
"0101 " # 18: ElidedFallbackNameID: 257
|
|
|
|
"7767 6874 " # 20: DesignAxis[0].AxisTag='wght'
|
|
|
|
"0102 " # 24: DesignAxis[0].AxisNameID=258 'Weight'
|
|
|
|
"0000 " # 26: DesignAxis[0].AxisOrdering=0
|
|
|
|
"0002 " # 28: AxisValueOffsets=[2] (+28)
|
|
|
|
"0003 " # 30: AxisValue[0].Format=3
|
|
|
|
"0000 0002 " # 32: AxisValue[0].AxisIndex=0, .Flags=0x2
|
|
|
|
"0002 " # 36: AxisValue[0].ValueNameID=2 'Regular'
|
|
|
|
"0190 0000 " # 38: AxisValue[0].Value=400.0
|
|
|
|
"02BC 0000 " # 42: AxisValue[0].LinkedValue=700.0
|
|
|
|
) # 46: <end>
|
|
|
|
assert len(STAT_DATA_VERSION_1_1) == 46
|
|
|
|
|
|
|
|
|
2016-12-21 13:24:51 +00:00
|
|
|
STAT_XML_VERSION_1_1 = [
|
|
|
|
'<Version value="0x00010001"/>',
|
|
|
|
'<DesignAxisRecordSize value="8"/>',
|
|
|
|
"<!-- DesignAxisCount=1 -->",
|
|
|
|
"<DesignAxisRecord>",
|
|
|
|
' <Axis index="0">',
|
|
|
|
' <AxisTag value="wght"/>',
|
|
|
|
' <AxisNameID value="258"/>',
|
|
|
|
' <AxisOrdering value="0"/>',
|
|
|
|
" </Axis>",
|
|
|
|
"</DesignAxisRecord>",
|
|
|
|
"<!-- AxisValueCount=1 -->",
|
|
|
|
"<AxisValueArray>",
|
|
|
|
' <AxisValue index="0" Format="3">',
|
|
|
|
' <AxisIndex value="0"/>',
|
2020-08-11 21:21:30 -07:00
|
|
|
' <Flags value="2"/> <!-- ElidableAxisValueName -->',
|
2016-12-21 13:24:51 +00:00
|
|
|
' <ValueNameID value="2"/>',
|
|
|
|
' <Value value="400.0"/>',
|
|
|
|
' <LinkedValue value="700.0"/>',
|
|
|
|
" </AxisValue>",
|
|
|
|
"</AxisValueArray>",
|
|
|
|
'<ElidedFallbackNameID value="257"/>',
|
|
|
|
]
|
2016-12-13 09:44:03 +01:00
|
|
|
|
|
|
|
|
2016-10-14 17:13:56 +02:00
|
|
|
class STATTest(unittest.TestCase):
|
2016-12-21 13:24:51 +00:00
|
|
|
@classmethod
|
|
|
|
def setUpClass(cls):
|
|
|
|
cls.maxDiff = None
|
|
|
|
|
2016-10-14 17:13:56 +02:00
|
|
|
def test_decompile_toXML(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
table.decompile(STAT_DATA, font=FakeFont([".notdef"]))
|
|
|
|
self.assertEqual(getXML(table.toXML), STAT_XML)
|
|
|
|
|
2016-12-02 19:12:26 -08:00
|
|
|
def test_decompile_toXML_withAxisJunk(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
table.decompile(STAT_DATA_WITH_AXIS_JUNK, font=FakeFont([".notdef"]))
|
|
|
|
self.assertEqual(getXML(table.toXML), STAT_XML_WITH_AXIS_JUNK)
|
2016-10-14 17:13:56 +02:00
|
|
|
|
|
|
|
def test_decompile_toXML_format3(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
table.decompile(STAT_DATA_AXIS_VALUE_FORMAT3, font=FakeFont([".notdef"]))
|
|
|
|
self.assertEqual(getXML(table.toXML), STAT_XML_AXIS_VALUE_FORMAT3)
|
|
|
|
|
2016-12-13 09:44:03 +01:00
|
|
|
def test_decompile_toXML_version_1_1(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
table.decompile(STAT_DATA_VERSION_1_1, font=FakeFont([".notdef"]))
|
|
|
|
self.assertEqual(getXML(table.toXML), STAT_XML_VERSION_1_1)
|
|
|
|
|
2016-12-21 09:53:32 +00:00
|
|
|
def test_compile_fromXML(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
font = FakeFont([".notdef"])
|
|
|
|
for name, attrs, content in parseXML(STAT_XML):
|
|
|
|
table.fromXML(name, attrs, content, font=font)
|
|
|
|
self.assertEqual(table.compile(font), STAT_DATA)
|
|
|
|
|
|
|
|
def test_compile_fromXML_withAxisJunk(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
font = FakeFont([".notdef"])
|
|
|
|
for name, attrs, content in parseXML(STAT_XML_WITH_AXIS_JUNK):
|
|
|
|
table.fromXML(name, attrs, content, font=font)
|
|
|
|
self.assertEqual(table.compile(font), STAT_DATA_WITH_AXIS_JUNK)
|
|
|
|
|
|
|
|
def test_compile_fromXML_format3(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
font = FakeFont([".notdef"])
|
|
|
|
for name, attrs, content in parseXML(STAT_XML_AXIS_VALUE_FORMAT3):
|
|
|
|
table.fromXML(name, attrs, content, font=font)
|
|
|
|
self.assertEqual(table.compile(font), STAT_DATA_AXIS_VALUE_FORMAT3)
|
|
|
|
|
|
|
|
def test_compile_fromXML_version_1_1(self):
|
|
|
|
table = newTable("STAT")
|
|
|
|
font = FakeFont([".notdef"])
|
|
|
|
for name, attrs, content in parseXML(STAT_XML_VERSION_1_1):
|
|
|
|
table.fromXML(name, attrs, content, font=font)
|
|
|
|
self.assertEqual(table.compile(font), STAT_DATA_VERSION_1_1)
|
|
|
|
|
2016-10-14 17:13:56 +02:00
|
|
|
|
|
|
|
if __name__ == "__main__":
|
2017-01-11 13:05:35 +00:00
|
|
|
import sys
|
2022-12-13 11:26:36 +00:00
|
|
|
|
2017-01-11 13:05:35 +00:00
|
|
|
sys.exit(unittest.main())
|