Don't cache charString bounds

https://github.com/fonttools/fonttools/pull/970#discussion_r117903692
This commit is contained in:
Masaya Nakamura 2017-08-01 10:35:39 +09:00
parent 22dfcd94a1
commit 3708f2c8d3
5 changed files with 25 additions and 30 deletions

View File

@ -2320,20 +2320,19 @@ class TopDict(BaseDict):
i = i + 1
def recalcFontBBox(self):
bounds = None
fontBBox = None
for charString in self.CharStrings.values():
if not hasattr(charString, 'bounds'):
charString.recalcBounds()
if charString.bounds is not None:
bounds = charString.calcBounds()
if bounds is not None:
bounds = unionRect(bounds, charString.bounds)
if fontBBox is not None:
fontBBox = unionRect(fontBBox, bounds)
else:
bounds = charString.bounds
fontBBox = bounds
if bounds is None:
if fontBBox is None:
self.FontBBox = self.defaults['FontBBox'][:]
else:
self.FontBBox = list(intRect(bounds))
self.FontBBox = list(intRect(fontBBox))
class FontDict(BaseDict):

View File

@ -978,10 +978,10 @@ class T2CharString(object):
extractor.execute(self)
self.width = extractor.width
def recalcBounds(self):
def calcBounds(self):
boundsPen = BoundsPen(None)
self.draw(boundsPen)
self.bounds = boundsPen.bounds
return boundsPen.bounds
def check_program(self, program, isCFF2=False):
if isCFF2:

View File

@ -65,11 +65,9 @@ class table__h_h_e_a(DefaultTable.DefaultTable):
topDict = ttFont['CFF '].cff.topDictIndex[0]
for name in ttFont.getGlyphOrder():
cs = topDict.CharStrings[name]
if not hasattr(cs, 'bounds'):
cs.recalcBounds()
if cs.bounds is None:
continue
boundsWidthDict[name] = math.ceil(cs.bounds[2]) - math.floor(cs.bounds[0])
bounds = cs.calcBounds()
if bounds is not None:
boundsWidthDict[name] = math.ceil(bounds[2]) - math.floor(bounds[0])
if boundsWidthDict:
minLeftSideBearing = float('inf')

View File

@ -64,11 +64,9 @@ class table__v_h_e_a(DefaultTable.DefaultTable):
topDict = ttFont['CFF '].cff.topDictIndex[0]
for name in ttFont.getGlyphOrder():
cs = topDict.CharStrings[name]
if not hasattr(cs, 'bounds'):
cs.recalcBounds()
if cs.bounds is None:
continue
boundsHeightDict[name] = math.ceil(cs.bounds[3]) - math.floor(cs.bounds[1])
bounds = cs.calcBounds()
if bounds is not None:
boundsHeightDict[name] = math.ceil(bounds[3]) - math.floor(bounds[1])
if boundsHeightDict:
minTopSideBearing = float('inf')

View File

@ -11,20 +11,20 @@ class T2CharStringTest(unittest.TestCase):
def stringToT2CharString(cls, string):
return T2CharString(program=stringToProgram(string), private=PrivateDict())
def test_recalcBounds_empty(self):
def test_calcBounds_empty(self):
cs = self.stringToT2CharString("endchar")
cs.recalcBounds()
self.assertEqual(cs.bounds, None)
bounds = cs.calcBounds()
self.assertEqual(bounds, None)
def test_recalcBounds_line(self):
def test_calcBounds_line(self):
cs = self.stringToT2CharString("100 100 rmoveto 40 10 rlineto -20 50 rlineto endchar")
cs.recalcBounds()
self.assertEqual(cs.bounds, (100, 100, 140, 160))
bounds = cs.calcBounds()
self.assertEqual(bounds, (100, 100, 140, 160))
def test_recalcBounds_curve(self):
def test_calcBounds_curve(self):
cs = self.stringToT2CharString("100 100 rmoveto -50 -150 200 0 -50 150 rrcurveto endchar")
cs.recalcBounds()
self.assertEqual(cs.bounds, (91.90524980688875, -12.5, 208.09475019311125, 100))
bounds = cs.calcBounds()
self.assertEqual(bounds, (91.90524980688875, -12.5, 208.09475019311125, 100))
if __name__ == "__main__":