Font with missing family causes test failure on OS X
From @Caleb Hattingh on #107:
====================================================================== FAIL: test_get_fonts (pygame.tests.font_test.FontModuleTest) ---------------------------------------------------------------------- Traceback (most recent call last): File "/Users/calebhattingh/temp/pygamewheel/env/lib/python3.5/site-packages/pygame/tests/font_test.py", line 94, in test_get_fonts self.failUnless(name.islower(), name) AssertionError: False is not true : ====================================================================== FAIL: test_get_fonts (pygame.tests.font_test.FontModuleTest) ---------------------------------------------------------------------- Traceback (most recent call last): File "/Users/calebhattingh/temp/pygamewheel/env/lib/python3.5/site-packages/pygame/tests/font_test.py", line 94, in test_get_fonts self.failUnless(name.islower(), name) AssertionError: False is not true : ---------------------------------------------------------------------- Ran 677 tests in 24.531s FAILED (failures=2)
Ok, I figured out why that font test is failing. One of the fonts on my system has a missing family field (GeezaPro.ttc). In pygame/sysfont.py, the output of /usr/bin/fc-list is parsed and when this font is processed, the family field is blank:
def initsysfonts_unix(path="fc-list"): """use the fc-list from fontconfig to get a list of fonts""" fonts = {} try: # note, we capture stderr so if fc-list isn't there to stop stderr # printing. flout, flerr = subprocess.Popen('%s : file family style' % path, shell=True, stdout=subprocess.PIPE, stderr=subprocess.PIPE, close_fds=True).communicate() except Exception: return fonts entries = toascii(flout) try: for line in entries.split('\n'): # <--- line = '/System/Library/Fonts/GeezaPro.ttc: :style=Regular,,Ordinr,Normal,Normaali,Regolare,,,Regulier,,,' try: filename, family, style = line.split(':', 2) # <--- filename = ''/System/Library/Fonts/GeezaPro.ttc', family = '', style = 'style=Regular,,Ordinr,Normal,Normaali,Regolare,,,Regulier,,,' if splitext(filename)[1].lower() in OpenType_extensions: bold = 'Bold' in style italic = 'Italic' in style oblique = 'Oblique' in style for name in family.split(','): if name: break else: name = splitext(basename(filename))[0] _addfont( _simplename(name), bold, italic or oblique, filename, fonts) except Exception: # try the next one. pass except Exception: pass return fonts
The family becomes the key in the Sysfonts dict. In font_tests.py
, function test_get_fonts()
calls pygame_font.get_fonts()
, which creates a list out of the Sysfonts keys, one of which is now an empty string. As a result, self.failUnless(name.islower(), name)
fails.
So basically, when building the Sysfonts dict, fonts with missing families should maybe be filtered out? Or given a generic name? I've no idea what the recommended behaviour for pygame might be.
Comments (6)
-
-
Yes, that's correct, sorry for the confusion:
>>> s = '/System/Library/Fonts/GeezaPro.ttc: :style=Regular,,Ordinr,Normal,Normaali,Regolare,,,Regulier,,,' >>> filename, family, style = s.split(':', 2) >>> filename, family, style ('/System/Library/Fonts/GeezaPro.ttc', ' ', 'style=Regular,,Ordinr,Normal,Normaali,Regolare,,,Regulier,,,')
-
If you change this line:
for name in family.split(','):
to this:
for name in family.strip().split(','):
Do the tests pass?
-
Very clever catch. Yes, with that change all tests now pass on my machine. (With the wheel. I have not rechecked building from source.)
-
- changed status to closed
-
- changed version to 1.9.2
- Log in to comment
It looks like fonts without a family name should get a name from the filename (i.e.
GeezaPro
in this case). Could it actually be getting the family name as' '
(i.e. a space), instead of an empty string?