Merge pull request #394 from anthrotype/psLib-py23
make t1Lib and psLib compatible with python 3
This commit is contained in:
commit
687a0e7ee3
@ -19,19 +19,35 @@ def _encryptChar(plain, R):
|
|||||||
|
|
||||||
|
|
||||||
def decrypt(cipherstring, R):
|
def decrypt(cipherstring, R):
|
||||||
|
r"""
|
||||||
|
>>> testStr = b"\0\0asdadads asds\265"
|
||||||
|
>>> decryptedStr, R = decrypt(testStr, 12321)
|
||||||
|
>>> decryptedStr == b'0d\nh\x15\xe8\xc4\xb2\x15\x1d\x108\x1a<6\xa1'
|
||||||
|
True
|
||||||
|
>>> R == 36142
|
||||||
|
True
|
||||||
|
"""
|
||||||
plainList = []
|
plainList = []
|
||||||
for cipher in cipherstring:
|
for cipher in cipherstring:
|
||||||
plain, R = _decryptChar(cipher, R)
|
plain, R = _decryptChar(cipher, R)
|
||||||
plainList.append(plain)
|
plainList.append(plain)
|
||||||
plainstring = strjoin(plainList)
|
plainstring = bytesjoin(plainList)
|
||||||
return plainstring, int(R)
|
return plainstring, int(R)
|
||||||
|
|
||||||
def encrypt(plainstring, R):
|
def encrypt(plainstring, R):
|
||||||
|
r"""
|
||||||
|
>>> testStr = b'0d\nh\x15\xe8\xc4\xb2\x15\x1d\x108\x1a<6\xa1'
|
||||||
|
>>> encryptedStr, R = encrypt(testStr, 12321)
|
||||||
|
>>> encryptedStr == b"\0\0asdadads asds\265"
|
||||||
|
True
|
||||||
|
>>> R == 36142
|
||||||
|
True
|
||||||
|
"""
|
||||||
cipherList = []
|
cipherList = []
|
||||||
for plain in plainstring:
|
for plain in plainstring:
|
||||||
cipher, R = _encryptChar(plain, R)
|
cipher, R = _encryptChar(plain, R)
|
||||||
cipherList.append(cipher)
|
cipherList.append(cipher)
|
||||||
cipherstring = strjoin(cipherList)
|
cipherstring = bytesjoin(cipherList)
|
||||||
return cipherstring, int(R)
|
return cipherstring, int(R)
|
||||||
|
|
||||||
|
|
||||||
@ -41,15 +57,11 @@ def hexString(s):
|
|||||||
|
|
||||||
def deHexString(h):
|
def deHexString(h):
|
||||||
import binascii
|
import binascii
|
||||||
h = strjoin(h.split())
|
h = bytesjoin(h.split())
|
||||||
return binascii.unhexlify(h)
|
return binascii.unhexlify(h)
|
||||||
|
|
||||||
|
|
||||||
def _test():
|
|
||||||
testStr = "\0\0asdadads asds\265"
|
|
||||||
print(decrypt, decrypt(testStr, 12321))
|
|
||||||
print(encrypt, encrypt(testStr, 12321))
|
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
if __name__ == "__main__":
|
||||||
_test()
|
import sys
|
||||||
|
import doctest
|
||||||
|
sys.exit(doctest.testmod().failed)
|
||||||
|
@ -7,15 +7,15 @@ import collections
|
|||||||
from string import whitespace
|
from string import whitespace
|
||||||
|
|
||||||
|
|
||||||
ps_special = '()<>[]{}%' # / is one too, but we take care of that one differently
|
ps_special = b'()<>[]{}%' # / is one too, but we take care of that one differently
|
||||||
|
|
||||||
skipwhiteRE = re.compile("[%s]*" % whitespace)
|
skipwhiteRE = re.compile(bytesjoin([b"[", whitespace, b"]*"]))
|
||||||
endofthingPat = "[^][(){}<>/%%%s]*" % whitespace
|
endofthingPat = bytesjoin([b"[^][(){}<>/%", whitespace, b"]*"])
|
||||||
endofthingRE = re.compile(endofthingPat)
|
endofthingRE = re.compile(endofthingPat)
|
||||||
commentRE = re.compile("%[^\n\r]*")
|
commentRE = re.compile(b"%[^\n\r]*")
|
||||||
|
|
||||||
# XXX This not entirely correct as it doesn't allow *nested* embedded parens:
|
# XXX This not entirely correct as it doesn't allow *nested* embedded parens:
|
||||||
stringPat = r"""
|
stringPat = br"""
|
||||||
\(
|
\(
|
||||||
(
|
(
|
||||||
(
|
(
|
||||||
@ -29,22 +29,44 @@ stringPat = r"""
|
|||||||
[^()]*
|
[^()]*
|
||||||
\)
|
\)
|
||||||
"""
|
"""
|
||||||
stringPat = "".join(stringPat.split())
|
stringPat = b"".join(stringPat.split())
|
||||||
stringRE = re.compile(stringPat)
|
stringRE = re.compile(stringPat)
|
||||||
|
|
||||||
hexstringRE = re.compile("<[%s0-9A-Fa-f]*>" % whitespace)
|
hexstringRE = re.compile(bytesjoin([b"<[", whitespace, b"0-9A-Fa-f]*>"]))
|
||||||
|
|
||||||
class PSTokenError(Exception): pass
|
class PSTokenError(Exception): pass
|
||||||
class PSError(Exception): pass
|
class PSError(Exception): pass
|
||||||
|
|
||||||
|
|
||||||
# StringIO.StringIO is only available in Python 2. The PSTokenizer class
|
class PSTokenizer(object):
|
||||||
# attemps to access private attributes from the latter which are not available
|
|
||||||
# in other file(-like) objects. Therefore, io.BytesIO (or io.StringIO) can't
|
def __init__(self, buf=b''):
|
||||||
# be used as ready replacements. For now we must drop Python3 support in psLib,
|
# Force self.buf to be a byte string
|
||||||
# and consequently in t1Lib, until we rewrite them for py23.
|
buf = tobytes(buf)
|
||||||
# See: https://github.com/behdad/fonttools/issues/391
|
self.buf = buf
|
||||||
class PSTokenizer(StringIO):
|
self.len = len(buf)
|
||||||
|
self.pos = 0
|
||||||
|
self.closed = False
|
||||||
|
|
||||||
|
def read(self, n=-1):
|
||||||
|
"""Read at most 'n' bytes from the buffer, or less if the read
|
||||||
|
hits EOF before obtaining 'n' bytes.
|
||||||
|
If 'n' is negative or omitted, read all data until EOF is reached.
|
||||||
|
"""
|
||||||
|
if self.closed:
|
||||||
|
raise ValueError("I/O operation on closed file")
|
||||||
|
if n is None or n < 0:
|
||||||
|
newpos = self.len
|
||||||
|
else:
|
||||||
|
newpos = min(self.pos+n, self.len)
|
||||||
|
r = self.buf[self.pos:newpos]
|
||||||
|
self.pos = newpos
|
||||||
|
return r
|
||||||
|
|
||||||
|
def close(self):
|
||||||
|
if not self.closed:
|
||||||
|
self.closed = True
|
||||||
|
del self.buf, self.pos
|
||||||
|
|
||||||
def getnexttoken(self,
|
def getnexttoken(self,
|
||||||
# localize some stuff, for performance
|
# localize some stuff, for performance
|
||||||
@ -53,32 +75,30 @@ class PSTokenizer(StringIO):
|
|||||||
stringmatch=stringRE.match,
|
stringmatch=stringRE.match,
|
||||||
hexstringmatch=hexstringRE.match,
|
hexstringmatch=hexstringRE.match,
|
||||||
commentmatch=commentRE.match,
|
commentmatch=commentRE.match,
|
||||||
endmatch=endofthingRE.match,
|
endmatch=endofthingRE.match):
|
||||||
whitematch=skipwhiteRE.match):
|
|
||||||
|
|
||||||
_, nextpos = whitematch(self.buf, self.pos).span()
|
self.skipwhite()
|
||||||
self.pos = nextpos
|
|
||||||
if self.pos >= self.len:
|
if self.pos >= self.len:
|
||||||
return None, None
|
return None, None
|
||||||
pos = self.pos
|
pos = self.pos
|
||||||
buf = self.buf
|
buf = self.buf
|
||||||
char = buf[pos]
|
char = bytechr(byteord(buf[pos]))
|
||||||
if char in ps_special:
|
if char in ps_special:
|
||||||
if char in '{}[]':
|
if char in b'{}[]':
|
||||||
tokentype = 'do_special'
|
tokentype = 'do_special'
|
||||||
token = char
|
token = char
|
||||||
elif char == '%':
|
elif char == b'%':
|
||||||
tokentype = 'do_comment'
|
tokentype = 'do_comment'
|
||||||
_, nextpos = commentmatch(buf, pos).span()
|
_, nextpos = commentmatch(buf, pos).span()
|
||||||
token = buf[pos:nextpos]
|
token = buf[pos:nextpos]
|
||||||
elif char == '(':
|
elif char == b'(':
|
||||||
tokentype = 'do_string'
|
tokentype = 'do_string'
|
||||||
m = stringmatch(buf, pos)
|
m = stringmatch(buf, pos)
|
||||||
if m is None:
|
if m is None:
|
||||||
raise PSTokenError('bad string at character %d' % pos)
|
raise PSTokenError('bad string at character %d' % pos)
|
||||||
_, nextpos = m.span()
|
_, nextpos = m.span()
|
||||||
token = buf[pos:nextpos]
|
token = buf[pos:nextpos]
|
||||||
elif char == '<':
|
elif char == b'<':
|
||||||
tokentype = 'do_hexstring'
|
tokentype = 'do_hexstring'
|
||||||
m = hexstringmatch(buf, pos)
|
m = hexstringmatch(buf, pos)
|
||||||
if m is None:
|
if m is None:
|
||||||
@ -88,7 +108,7 @@ class PSTokenizer(StringIO):
|
|||||||
else:
|
else:
|
||||||
raise PSTokenError('bad token at character %d' % pos)
|
raise PSTokenError('bad token at character %d' % pos)
|
||||||
else:
|
else:
|
||||||
if char == '/':
|
if char == b'/':
|
||||||
tokentype = 'do_literal'
|
tokentype = 'do_literal'
|
||||||
m = endmatch(buf, pos+1)
|
m = endmatch(buf, pos+1)
|
||||||
else:
|
else:
|
||||||
@ -99,6 +119,7 @@ class PSTokenizer(StringIO):
|
|||||||
_, nextpos = m.span()
|
_, nextpos = m.span()
|
||||||
token = buf[pos:nextpos]
|
token = buf[pos:nextpos]
|
||||||
self.pos = pos + len(token)
|
self.pos = pos + len(token)
|
||||||
|
token = tostr(token, encoding='ascii')
|
||||||
return tokentype, token
|
return tokentype, token
|
||||||
|
|
||||||
def skipwhite(self, whitematch=skipwhiteRE.match):
|
def skipwhite(self, whitematch=skipwhiteRE.match):
|
||||||
@ -107,7 +128,6 @@ class PSTokenizer(StringIO):
|
|||||||
|
|
||||||
def starteexec(self):
|
def starteexec(self):
|
||||||
self.pos = self.pos + 1
|
self.pos = self.pos + 1
|
||||||
#self.skipwhite()
|
|
||||||
self.dirtybuf = self.buf[self.pos:]
|
self.dirtybuf = self.buf[self.pos:]
|
||||||
self.buf, R = eexec.decrypt(self.dirtybuf, 55665)
|
self.buf, R = eexec.decrypt(self.dirtybuf, 55665)
|
||||||
self.len = len(self.buf)
|
self.len = len(self.buf)
|
||||||
@ -119,11 +139,6 @@ class PSTokenizer(StringIO):
|
|||||||
self.buf = self.dirtybuf
|
self.buf = self.dirtybuf
|
||||||
del self.dirtybuf
|
del self.dirtybuf
|
||||||
|
|
||||||
def flush(self):
|
|
||||||
if self.buflist:
|
|
||||||
self.buf = self.buf + "".join(self.buflist)
|
|
||||||
self.buflist = []
|
|
||||||
|
|
||||||
|
|
||||||
class PSInterpreter(PSOperators):
|
class PSInterpreter(PSOperators):
|
||||||
|
|
||||||
@ -163,7 +178,6 @@ class PSInterpreter(PSOperators):
|
|||||||
try:
|
try:
|
||||||
while 1:
|
while 1:
|
||||||
tokentype, token = getnexttoken()
|
tokentype, token = getnexttoken()
|
||||||
#print token
|
|
||||||
if not token:
|
if not token:
|
||||||
break
|
break
|
||||||
if tokentype:
|
if tokentype:
|
||||||
@ -345,12 +359,3 @@ def suckfont(data):
|
|||||||
rawfont = fontdir[fontNames[0]]
|
rawfont = fontdir[fontNames[0]]
|
||||||
interpreter.close()
|
interpreter.close()
|
||||||
return unpack_item(rawfont)
|
return unpack_item(rawfont)
|
||||||
|
|
||||||
|
|
||||||
if __name__ == "__main__":
|
|
||||||
import EasyDialogs
|
|
||||||
path = EasyDialogs.AskFileForOpen()
|
|
||||||
if path:
|
|
||||||
from fontTools import t1Lib
|
|
||||||
data, kind = t1Lib.read(path)
|
|
||||||
font = suckfont(data)
|
|
||||||
|
@ -13,7 +13,7 @@ write(path, data, kind='OTHER', dohex=False)
|
|||||||
'kind' can be one of 'LWFN', 'PFB' or 'OTHER'; it defaults to 'OTHER'.
|
'kind' can be one of 'LWFN', 'PFB' or 'OTHER'; it defaults to 'OTHER'.
|
||||||
'dohex' is a flag which determines whether the eexec encrypted
|
'dohex' is a flag which determines whether the eexec encrypted
|
||||||
part should be written as hexadecimal or binary, but only if kind
|
part should be written as hexadecimal or binary, but only if kind
|
||||||
is 'LWFN' or 'PFB'.
|
is 'OTHER'.
|
||||||
"""
|
"""
|
||||||
from __future__ import print_function, division, absolute_import
|
from __future__ import print_function, division, absolute_import
|
||||||
from fontTools.misc.py23 import *
|
from fontTools.misc.py23 import *
|
||||||
@ -36,7 +36,6 @@ except ImportError:
|
|||||||
haveMacSupport = 0
|
haveMacSupport = 0
|
||||||
else:
|
else:
|
||||||
haveMacSupport = 1
|
haveMacSupport = 1
|
||||||
import MacOS
|
|
||||||
|
|
||||||
|
|
||||||
class T1Error(Exception): pass
|
class T1Error(Exception): pass
|
||||||
@ -56,8 +55,8 @@ class T1Font(object):
|
|||||||
else:
|
else:
|
||||||
pass # XXX
|
pass # XXX
|
||||||
|
|
||||||
def saveAs(self, path, type):
|
def saveAs(self, path, type, dohex=False):
|
||||||
write(path, self.getData(), type)
|
write(path, self.getData(), type, dohex)
|
||||||
|
|
||||||
def getData(self):
|
def getData(self):
|
||||||
# XXX Todo: if the data has been converted to Python object,
|
# XXX Todo: if the data has been converted to Python object,
|
||||||
@ -266,7 +265,7 @@ def writeOther(path, data, dohex=False):
|
|||||||
if code == 2 and dohex:
|
if code == 2 and dohex:
|
||||||
while chunk:
|
while chunk:
|
||||||
f.write(eexec.hexString(chunk[:hexlinelen]))
|
f.write(eexec.hexString(chunk[:hexlinelen]))
|
||||||
f.write('\r')
|
f.write(b'\r')
|
||||||
chunk = chunk[hexlinelen:]
|
chunk = chunk[hexlinelen:]
|
||||||
else:
|
else:
|
||||||
f.write(chunk)
|
f.write(chunk)
|
||||||
@ -276,13 +275,13 @@ def writeOther(path, data, dohex=False):
|
|||||||
|
|
||||||
# decryption tools
|
# decryption tools
|
||||||
|
|
||||||
EEXECBEGIN = "currentfile eexec"
|
EEXECBEGIN = b"currentfile eexec"
|
||||||
EEXECEND = '0' * 64
|
EEXECEND = b'0' * 64
|
||||||
EEXECINTERNALEND = "currentfile closefile"
|
EEXECINTERNALEND = b"currentfile closefile"
|
||||||
EEXECBEGINMARKER = "%-- eexec start\r"
|
EEXECBEGINMARKER = b"%-- eexec start\r"
|
||||||
EEXECENDMARKER = "%-- eexec end\r"
|
EEXECENDMARKER = b"%-- eexec end\r"
|
||||||
|
|
||||||
_ishexRE = re.compile('[0-9A-Fa-f]*$')
|
_ishexRE = re.compile(b'[0-9A-Fa-f]*$')
|
||||||
|
|
||||||
def isHex(text):
|
def isHex(text):
|
||||||
return _ishexRE.match(text) is not None
|
return _ishexRE.match(text) is not None
|
||||||
@ -300,7 +299,7 @@ def decryptType1(data):
|
|||||||
if decrypted[-len(EEXECINTERNALEND)-1:-1] != EEXECINTERNALEND \
|
if decrypted[-len(EEXECINTERNALEND)-1:-1] != EEXECINTERNALEND \
|
||||||
and decrypted[-len(EEXECINTERNALEND)-2:-2] != EEXECINTERNALEND:
|
and decrypted[-len(EEXECINTERNALEND)-2:-2] != EEXECINTERNALEND:
|
||||||
raise T1Error("invalid end of eexec part")
|
raise T1Error("invalid end of eexec part")
|
||||||
decrypted = decrypted[:-len(EEXECINTERNALEND)-2] + '\r'
|
decrypted = decrypted[:-len(EEXECINTERNALEND)-2] + b'\r'
|
||||||
data.append(EEXECBEGINMARKER + decrypted + EEXECENDMARKER)
|
data.append(EEXECBEGINMARKER + decrypted + EEXECENDMARKER)
|
||||||
else:
|
else:
|
||||||
if chunk[-len(EEXECBEGIN)-1:-1] == EEXECBEGIN:
|
if chunk[-len(EEXECBEGIN)-1:-1] == EEXECBEGIN:
|
||||||
@ -333,7 +332,7 @@ def findEncryptedChunks(data):
|
|||||||
return chunks
|
return chunks
|
||||||
|
|
||||||
def deHexString(hexstring):
|
def deHexString(hexstring):
|
||||||
return eexec.deHexString(strjoin(hexstring.split()))
|
return eexec.deHexString(bytesjoin(hexstring.split()))
|
||||||
|
|
||||||
|
|
||||||
# Type 1 assertion
|
# Type 1 assertion
|
||||||
@ -357,7 +356,7 @@ def assertType1(data):
|
|||||||
# pfb helpers
|
# pfb helpers
|
||||||
|
|
||||||
def longToString(long):
|
def longToString(long):
|
||||||
s = ""
|
s = b""
|
||||||
for i in range(4):
|
for i in range(4):
|
||||||
s += bytechr((long & (0xff << (i * 8))) >> i * 8)
|
s += bytechr((long & (0xff << (i * 8))) >> i * 8)
|
||||||
return s
|
return s
|
86
Lib/fontTools/t1Lib/t1Lib_test.py
Normal file
86
Lib/fontTools/t1Lib/t1Lib_test.py
Normal file
@ -0,0 +1,86 @@
|
|||||||
|
from __future__ import print_function, division, absolute_import
|
||||||
|
from fontTools.misc.py23 import *
|
||||||
|
import unittest
|
||||||
|
import os
|
||||||
|
from fontTools import t1Lib
|
||||||
|
from fontTools.pens.basePen import NullPen
|
||||||
|
import random
|
||||||
|
|
||||||
|
|
||||||
|
CWD = os.path.abspath(os.path.dirname(__file__))
|
||||||
|
DATADIR = os.path.join(CWD, 'testdata')
|
||||||
|
PFA = os.path.join(DATADIR, 'TestT1-Regular.pfa')
|
||||||
|
PFB = os.path.join(DATADIR, 'TestT1-Regular.pfb')
|
||||||
|
|
||||||
|
|
||||||
|
class FindEncryptedChunksTest(unittest.TestCase):
|
||||||
|
|
||||||
|
def test_findEncryptedChunks(self):
|
||||||
|
with open(PFA, "rb") as f:
|
||||||
|
data = f.read()
|
||||||
|
chunks = t1Lib.findEncryptedChunks(data)
|
||||||
|
self.assertEqual(len(chunks), 3)
|
||||||
|
self.assertFalse(chunks[0][0])
|
||||||
|
# the second chunk is encrypted
|
||||||
|
self.assertTrue(chunks[1][0])
|
||||||
|
self.assertFalse(chunks[2][0])
|
||||||
|
|
||||||
|
|
||||||
|
class DecryptType1Test(unittest.TestCase):
|
||||||
|
|
||||||
|
def test_decryptType1(self):
|
||||||
|
with open(PFA, "rb") as f:
|
||||||
|
data = f.read()
|
||||||
|
decrypted = t1Lib.decryptType1(data)
|
||||||
|
self.assertNotEqual(decrypted, data)
|
||||||
|
|
||||||
|
|
||||||
|
class ReadWriteTest(unittest.TestCase):
|
||||||
|
|
||||||
|
def test_read_pfa_write_pfb(self):
|
||||||
|
font = t1Lib.T1Font(PFA)
|
||||||
|
data = self.write(font, 'PFB')
|
||||||
|
self.assertEqual(font.getData(), data)
|
||||||
|
|
||||||
|
def test_read_pfb_write_pfa(self):
|
||||||
|
font = t1Lib.T1Font(PFB)
|
||||||
|
# 'OTHER' == 'PFA'
|
||||||
|
data = self.write(font, 'OTHER', dohex=True)
|
||||||
|
self.assertEqual(font.getData(), data)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def write(font, outtype, dohex=False):
|
||||||
|
temp = os.path.join(DATADIR, 'temp.' + outtype.lower())
|
||||||
|
try:
|
||||||
|
font.saveAs(temp, outtype, dohex=dohex)
|
||||||
|
newfont = t1Lib.T1Font(temp)
|
||||||
|
data = newfont.getData()
|
||||||
|
finally:
|
||||||
|
if os.path.exists(temp):
|
||||||
|
os.remove(temp)
|
||||||
|
return data
|
||||||
|
|
||||||
|
|
||||||
|
class T1FontTest(unittest.TestCase):
|
||||||
|
|
||||||
|
def test_parse_pfa(self):
|
||||||
|
font = t1Lib.T1Font(PFA)
|
||||||
|
font.parse()
|
||||||
|
self.assertEqual(font['FontName'], 'TestT1-Regular')
|
||||||
|
self.assertTrue('Subrs' in font['Private'])
|
||||||
|
|
||||||
|
def test_parse_pfb(self):
|
||||||
|
font = t1Lib.T1Font(PFB)
|
||||||
|
font.parse()
|
||||||
|
self.assertEqual(font['FontName'], 'TestT1-Regular')
|
||||||
|
self.assertTrue('Subrs' in font['Private'])
|
||||||
|
|
||||||
|
def test_getGlyphSet(self):
|
||||||
|
font = t1Lib.T1Font(PFA)
|
||||||
|
glyphs = font.getGlyphSet()
|
||||||
|
i = random.randrange(len(glyphs))
|
||||||
|
aglyph = list(glyphs.values())[i]
|
||||||
|
self.assertTrue(hasattr(aglyph, 'draw'))
|
||||||
|
self.assertFalse(hasattr(aglyph, 'width'))
|
||||||
|
aglyph.draw(NullPen())
|
||||||
|
self.assertTrue(hasattr(aglyph, 'width'))
|
60
Lib/fontTools/t1Lib/testdata/TestT1-Regular.pfa
vendored
Normal file
60
Lib/fontTools/t1Lib/testdata/TestT1-Regular.pfa
vendored
Normal file
@ -0,0 +1,60 @@
|
|||||||
|
%!FontType1-1.1: TestT1-Regular 1.0
|
||||||
|
%%BeginResource: font TestT1-Regular
|
||||||
|
12 dict dup begin
|
||||||
|
/FontType 1 def
|
||||||
|
/FontName /TestT1-Regular def
|
||||||
|
/FontInfo 14 dict dup begin
|
||||||
|
/version (1.0) def
|
||||||
|
/Notice (Test T1 is not a trademark of FontTools.) def
|
||||||
|
/Copyright (Copyright c 2015 by FontTools. No rights reserved.) def
|
||||||
|
/FullName (Test T1) def
|
||||||
|
/FamilyName (Test T1) def
|
||||||
|
/Weight (Regular) def
|
||||||
|
/ItalicAngle 0.000000 def
|
||||||
|
/isFixedPitch false def
|
||||||
|
/UnderlinePosition -75.000000 def
|
||||||
|
/UnderlineThickness 50.000000 def
|
||||||
|
/FSType 0 def
|
||||||
|
end def
|
||||||
|
/PaintType 0 def
|
||||||
|
/FontMatrix [0.001 0 0 0.001 0 0] def
|
||||||
|
/Encoding 256 array
|
||||||
|
0 1 255 {1 index exch /.notdef put} for
|
||||||
|
def
|
||||||
|
/FontBBox {50.000000 0.000000 668.000000 750.000000} def
|
||||||
|
end
|
||||||
|
currentfile eexec bab431ea06bb0a1031e1aa11919e714ac1ac5197cb08b39a4d7e746fca0af12d89ac0ebd1bc11ab1
|
||||||
|
b3887b922efcec739534242d2fd22e7c30e3edce24b93798627e1ac3387816a8c4b84d76047dada8
|
||||||
|
28b2ad27c5603046fecbc2a97adc5c37a68912324d2d435f2ee0ccc38df10ba1271a1c9af8897a6d
|
||||||
|
6e425cd7d18fd6bd64c2adadb74365bc101a850841669886291e158cbfa7f204b3fe0ba49ffe0c80
|
||||||
|
4f6795d32eb770c5fcd38a3879c06a4bb87b2d3ab100d8c2b5f89e9be99248575575025c66381446
|
||||||
|
e4d9183674880aef57fb2032a1e00431133b16f6d758de7c3d0c48a0fada1d40034742a69fb3a6f9
|
||||||
|
450d2251e659158a04697cbfa70907346d27d37ef683284385c44a1b5089bd29b4629b6483122dc8
|
||||||
|
cbce7327bdc33dd30e6fcdb346c0ddaf433a5ac740423aa35639b2386673832f5ae8cc380e9703ba
|
||||||
|
d3369533bfa85af9f56a090c9d97f5fc26ed102c07b647137e83632be51a65a532bd26430b59a31c
|
||||||
|
3cb037ded351c1d4e944733feb30a3e6f81c1a7b74ac4e0eadbe705412d47991c246e8820876bbc6
|
||||||
|
1f6a3e264ae6b2ad4b864b0d7abee289308bea26eb15d00d2b9103861386e0a5f1802ba06f916810
|
||||||
|
62110d2b1c3641806f78eea365614f440b580185e84bac6f87bee36108d95174c786600cf0e9dc4a
|
||||||
|
5545d1a84cfe8392115c0b7027c17fd460481d21f684af32204085690946327bfded992852645149
|
||||||
|
8d44150d2495bd2efe0db6a450c6e28d0a52ca234e252129d5095596b0d8de096682d2eb00bc8320
|
||||||
|
f257fd653b05a22eab7a193ccc315a6ee274a03ff1fdf443b310157a02656ca4b06c581dca8ced72
|
||||||
|
c6ddcab26eb856ad1093452c587438b7f8408c1311e19254955914612c09828fd4d4fc2b8b0406ea
|
||||||
|
2ee38348a8bdab88a77b8033366b2e469834c01b7bd73207b7c67756937c7a9232947fde2e0ea327
|
||||||
|
7b7d610e601b91389ccbcdd813c87db5333c0c723e48d3ef69285f246327978ce68ae9081076a227
|
||||||
|
1a962a2a10e2b1147ec40b0f6553a00c8b329118569d16fe04a4fa195caf1b04c52c9a562b72e0cd
|
||||||
|
e411d747af796b9d2fb086ed927efb0e5fc9f50aa18aaf4949cba0de0805210620a19eec4319dfef
|
||||||
|
a74d9d13d16f8ad793323a231347e6b40022a1100c1e064b8679c1da63a26dfb217a6037096ad796
|
||||||
|
320da5a9d0526eed51d7d64d3223e285c1a8c70780c59ecc9dd9bc90a0f84ffa038834918cebe247
|
||||||
|
f6e8fa4ca0654019196388f2df008e63bc32c8e5e686dbb69193b7749638c22b389fb1f090fbb007
|
||||||
|
fdb8a6ee4e4b29e123fe1652fe72239bd2c8
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
0000000000000000000000000000000000000000000000000000000000000000
|
||||||
|
cleartomark
|
||||||
|
%%EndResource
|
||||||
|
%%EOF
|
BIN
Lib/fontTools/t1Lib/testdata/TestT1-Regular.pfb
vendored
Normal file
BIN
Lib/fontTools/t1Lib/testdata/TestT1-Regular.pfb
vendored
Normal file
Binary file not shown.
Loading…
x
Reference in New Issue
Block a user