From: <jo...@us...> - 2007-09-30 20:08:57
|
Revision: 3901 http://matplotlib.svn.sourceforge.net/matplotlib/?rev=3901&view=rev Author: jouni Date: 2007-09-30 13:08:50 -0700 (Sun, 30 Sep 2007) Log Message: ----------- use_tex in pdf backend: don't use AFM files, which are not there in some TeX distros Modified Paths: -------------- trunk/matplotlib/lib/matplotlib/backends/backend_pdf.py trunk/matplotlib/lib/matplotlib/dviread.py Modified: trunk/matplotlib/lib/matplotlib/backends/backend_pdf.py =================================================================== --- trunk/matplotlib/lib/matplotlib/backends/backend_pdf.py 2007-09-28 15:57:49 UTC (rev 3900) +++ trunk/matplotlib/lib/matplotlib/backends/backend_pdf.py 2007-09-30 20:08:50 UTC (rev 3901) @@ -500,70 +500,15 @@ finally: fh.close() - fh = open(fontinfo.afmfile, 'rb') - matplotlib.verbose.report( - 'Reading metrics from ' + fontinfo.afmfile, 'debug') - try: - afmdata = AFM(fh) - finally: - fh.close() - font = FT2Font(filename) - font.attach_file(fontinfo.afmfile) widthsObject, fontdescObject, fontdictObject, fontfileObject = \ [ self.reserveObject(n) for n in ('font widths', 'font descriptor', 'font dictionary', 'font file') ] - _, _, fullname, familyname, weight, italic_angle, fixed_pitch, \ - ul_position, ul_thickness = font.get_ps_font_info() - - if fontinfo.encodingfile is not None: - enc = dviread.Encoding(fontinfo.encodingfile) - widths = [] - for ch in enc: - try: - widths.append(afmdata.get_width_from_char_name(ch)) - except KeyError: - matplotlib.verbose.report( - 'No width for %s in %s' % (ch, fullname), 'debug-annoying') - widths.append(0) - - differencesArray = [ Name(ch) for ch in enc ] - differencesArray = [ 0 ] + differencesArray - firstchar = 0 - lastchar = len(differencesArray) - 2 - else: - widths = [ None for i in range(256) ] - for ch in range(256): - try: - widths[ch] = afmdata.get_width_char(ch, isord=True) - except KeyError: - pass - not_None = [ch for ch in range(256) - if widths[ch] is not None] - firstchar = not_None[0] - lastchar = not_None[-1] - widths = widths[firstchar:lastchar+1] - for i,w in enumerate(widths): - if w is None: widths[i] = 0 - - differencesArray = [ ] - need_idx = True - for ch in range(firstchar, lastchar+1): - try: - name = afmdata.get_name_char(ch, isord=True) - if need_idx: - differencesArray.append(ch) - need_idx = False - differencesArray.append(Name(name)) - except KeyError: - matplotlib.verbose.report( - 'No name for glyph %d in %s' % (ch, fullname), - 'debug-annoying') - need_idx = True - + firstchar = 0 + lastchar = len(fontinfo.widths) - 1 fontdict = { 'Type': Name('Font'), @@ -575,15 +520,22 @@ 'FontDescriptor': fontdescObject, } - fontdict.update({ - 'Encoding': { 'Type': Name('Encoding'), - 'Differences': differencesArray }, - }) + if fontinfo.encodingfile is not None: + enc = dviread.Encoding(fontinfo.encodingfile) + differencesArray = [ Name(ch) for ch in enc ] + differencesArray = [ 0 ] + differencesArray + fontdict.update({ + 'Encoding': { 'Type': Name('Encoding'), + 'Differences': differencesArray }, + }) + _, _, fullname, familyname, weight, italic_angle, fixed_pitch, \ + ul_position, ul_thickness = font.get_ps_font_info() + flags = 0 if fixed_pitch: flags |= 1 << 0 # fixed width if 0: flags |= 1 << 1 # TODO: serif - if 1: flags |= 1 << 2 # TODO: symbolic + if 1: flags |= 1 << 2 # TODO: symbolic (most TeX fonts are) else: flags |= 1 << 5 # non-symbolic if italic_angle: flags |= 1 << 6 # italic if 0: flags |= 1 << 16 # TODO: all caps @@ -598,33 +550,17 @@ 'ItalicAngle': italic_angle, 'Ascent': font.ascender, 'Descent': font.descender, - 'CapHeight': 1000, # default guess if missing from AFM file - 'XHeight': afmdata.get_xheight(), + 'CapHeight': 1000, # TODO: find this out + 'XHeight': 500, # TODO: this one too 'FontFile': fontfileObject, 'FontFamily': familyname, + 'StemV': 50, # TODO + # (see also revision 3874; but not all TeX distros have AFM files!) #'FontWeight': a number where 400 = Regular, 700 = Bold } - try: - descriptor['CapHeight'] = afmdata.get_capheight() - except KeyError: - pass - # StemV is obligatory in PDF font descriptors but optional in - # AFM files. The collection of AFM files in my TeX Live 2007 - # collection has values ranging from 22 to 219, with both - # median and mode 50, so if the AFM file is silent, I'm - # guessing 50. -JKS - StemV = afmdata.get_vertical_stem_width() - if StemV is None: StemV = 50 - descriptor['StemV'] = StemV - - # StemH is entirely optional: - StemH = afmdata.get_horizontal_stem_width() - if StemH is not None: - descriptor['StemH'] = StemH - self.writeObject(fontdictObject, fontdict) - self.writeObject(widthsObject, widths) + self.writeObject(widthsObject, fontinfo.widths) self.writeObject(fontdescObject, descriptor) t1font = type1font.Type1Font(filename) @@ -1470,16 +1406,13 @@ oldfont, seq = None, [] for x1, y1, dvifont, glyph, width in page.text: if dvifont != oldfont: - fontinfo = self.tex_font_mapping(dvifont.texname) - pdfname = self.file.fontName(fontinfo.filename) - if not fontinfo.afm: - matplotlib.verbose.report( - 'RendererPdf.draw_tex: No AFM file found for %s (%s)' \ - % (dvifont.texname, fontinfo.filename), - 'helpful') - self.file.fontInfo[pdfname] = Bunch( - encodingfile=fontinfo.encoding, - afmfile=fontinfo.afm) + psfont = self.tex_font_mapping(dvifont.texname) + pdfname = self.file.fontName(psfont.filename) + if self.file.fontInfo.get(pdfname, None) is None: + self.file.fontInfo[pdfname] = Bunch( + encodingfile=psfont.encoding, + widths=dvifont.widths, + dvifont=dvifont) seq += [['font', pdfname, dvifont.size]] oldfont = dvifont seq += [['text', x1, y1, [chr(glyph)], x1+width]] Modified: trunk/matplotlib/lib/matplotlib/dviread.py =================================================================== --- trunk/matplotlib/lib/matplotlib/dviread.py 2007-09-28 15:57:49 UTC (rev 3900) +++ trunk/matplotlib/lib/matplotlib/dviread.py 2007-09-30 20:08:50 UTC (rev 3901) @@ -84,7 +84,7 @@ e = 0 # zero depth else: # glyph x,y,font,g,w = elt - h = _mul2012(font._scale, font._tfm.height[g]) + h = _mul2012(font._scale, font._tfm.height[g]) e = _mul2012(font._scale, font._tfm.depth[g]) minx = min(minx, x) miny = min(miny, y - h) @@ -380,19 +380,21 @@ class DviFont(object): """ - Object that holds a font's texname and size and supports comparison. + Object that holds a font's texname and size, supports comparison, + and knows the widths of glyphs in the same units as the AFM file. There are also internal attributes (for use by dviread.py) that are _not_ used for comparison. The size is in Adobe points (converted from TeX points). """ - __slots__ = ('texname', 'size', '_scale', '_vf', '_tfm') + __slots__ = ('texname', 'size', 'widths', '_scale', '_vf', '_tfm') def __init__(self, scale, tfm, texname, vf): self._scale, self._tfm, self.texname, self._vf = \ scale, tfm, texname, vf - # TODO: would it make more sense to have the size in dpi units? self.size = scale * (72.0 / (72.27 * 2**16)) + self.widths = [ (1000*tfm.width.get(char, 0)) >> 20 + for char in range(0, max(tfm.width)) ] def __eq__(self, other): return self.__class__ == other.__class__ and \ @@ -402,6 +404,10 @@ return not self.__eq__(other) def _width_of(self, char): + """ + Width of char in dvi units. For internal use by dviread.py. + """ + width = self._tfm.width.get(char, None) if width is not None: return _mul2012(width, self._scale) @@ -598,7 +604,6 @@ fn, enc = result.filename, result.encoding if fn is not None and not fn.startswith('/'): result.filename = find_tex_file(fn) - result.afm = find_tex_file(fn[:-4] + '.afm') if enc is not None and not enc.startswith('/'): result.encoding = find_tex_file(result.encoding) return result This was sent by the SourceForge.net collaborative development platform, the world's largest Open Source development site. |