%! % Get the Font Metric Information from a font % Written by W.T. Roberts, Queen Mary College, LONDON UK % (liam@cs.qmc.ac.uk, liam@qmc-cs.UUCP) % modified 3/91 by Bryan Bayerdorffer, UT Austin, Austin, TX, USA % (bryan@cs.utexas.edu) % modified 4/93 by Thomas Wolff (wolff@inf.fu-berlin.de): % must discard UniqueID as well as FID when generating modified font copy % ligature information must only be printed if ligatures are present % the availability of the four CapHeight etc entries is decided separately % to allow CapHeight to be generated even if the font does not % contain small characters % if no CapHeight can be determined (because there is no letter "H") the % height value of FontBBox is taken instead - Adobe's makepfm % program requires the presence of this entry % moved the FontName line behind the Comment lines % added the EncodingScheme information % now printing FontInfo contents in well-defined order % added character count in StartCharMetrics % changed BBox information for null characters to 0 0 0 0 % don't generate entries for undefined characters, even if included in % the font's encoding % getmetric0 variant leaves out final "End..." entries to simplify % merging in kerning and composite information from other sources % added code for automatic new font name detection to enable cooperation % with simple MSDOS batch script %statusdict begin 0 setjobtimeout end /xdef {exch def} def /sp {( ) print} def /nl {(\n) print flush} def /eof {(\034) print flush} def %Amiga end-of-file /= { %dup type (stringtype) ne { buffer cvs %} if print} def /toupper { dup dup (a) 0 get ge exch (z) 0 get le and {(a) 0 get sub (A) 0 get add} if % convert to lowercase } def /buffer 250 string def /getmetric0 { % /VMsave save def dup findfont /fontdict xdef % grab the font (StartFontMetrics 1.0) print nl (Comment generated by getmetric.ps (by W.T. Roberts, qmc-cs.UUCP)) print nl (Comment (modified 3/91 by Bryan Bayerdorffer, 4/93 by Thomas Wolff)) print nl (FontName ) print = nl % record PostScript name getFontInfo getEncodingScheme getFontBBox iniBBox recorddefaults % get the default encoding miscHeights recordunencoded (StartCharMetrics ) print #name = nl getCharMetrics checkBBox % VMsave restore } def /getmetric { getmetric0 (EndCharMetrics) print nl (EndFontMetrics) print nl } def /iniBBox { /llx 1000 def /lly 1000 def /urx -1000 def /ury -1000 def } def /checkBBox { llx BBllx 1 sub lt lly BBlly 1 sub lt urx BBurx 1 add gt ury BBury 1 add gt or or or {(Comment calculated FontBBox) print ury urx lly llx 4 {sp =} repeat % convert to 1000 point and print nl } if } def /getFontInfo { fontdict /FontInfo known {fontdict /FontInfo get {exch buffer cvs dup dup 0 get toupper 0 exch put % convert first letter to UC print sp = nl} forall } if } def /getFontInfo { fontdict /FontInfo known {fontdict /FontInfo get [/FullName /FamilyName /Weight /ItalicAngle /isFixedPitch /UnderlinePosition /UnderlineThickness /version /Notice] {2 copy known {2 copy get exch buffer cvs dup dup 0 get toupper 0 exch put % convert first letter to upper case print sp = nl} {pop} ifelse } forall } if } def /getFontBBox { fontdict /FontMatrix get dup length array /fmat xdef fmat copy pop fontdict /FontBBox get aload pop % llx lly trx try fmat transform 4 2 roll fmat transform % TRX TRY LLX LLY 4 {1000 mul round cvi 4 1 roll} repeat % convert to 1000 point (FontBBox) print 4 copy /BBlly xdef /BBllx xdef /BBury xdef /BBurx xdef 2 {exch sp = sp =} repeat nl } def /getEncodingScheme { /EncodingScheme (FontSpecific) def % the default fontdict /Encoding get dup StandardEncoding eq {/EncodingScheme (AdobeStandardEncoding) def} if dup SymbolEncoding eq {/EncodingScheme (SymbolEncoding) def} if % others... pop (EncodingScheme ) print EncodingScheme print nl } def /maketempfont { % encoding vector fontdict length dict /testdict xdef fontdict { 1 index dup /FID ne exch /UniqueID ne and {testdict 3 1 roll put} {pop pop} ifelse } forall % copy contents of fontdict testdict begin /Encoding encoding def end % install the encoding vector /TestName testdict definefont 1000 scalefont setfont } def /recorddefaults { fontdict /CharStrings known {fontdict /CharStrings get length 256 gt {fontdict /CharStrings get length} {256} ifelse} {256} ifelse array /names xdef % make array to hold the names /#name 0 def /defaultEncoding 256 dict def fontdict begin defaultEncoding begin 0 1 Encoding length 1 sub {dup Encoding exch get dup dup /.notdef ne % ignore .notdef ... exch fontdict /CharStrings known {fontdict /CharStrings get exch known} % and undefined characters {pop true} ifelse and {dup recordname exch def} {pop pop} ifelse % record number } for end end } def /recordname { userdict begin names exch #name exch put /#name #name 1 add def end } def /recordunencoded { fontdict /CharStrings known {fontdict /CharStrings get {pop dup dup /.notdef eq exch % ignore .notdef defaultEncoding exch known or % and defaultEncoding names {pop} {recordname} ifelse } forall } if } def /getCharMetrics { 256 array /encoding xdef /namecount #name def /first 0 def % while (true) {namecount 256 le {names first namecount getinterval} {names first 256 getinterval} ifelse encoding copy pop maketempfont 0 1 encoding length namecount le {encoding length 1 sub} {namecount 1 sub} ifelse {getcharmetric} for /namecount namecount 256 sub def /first first 256 add def namecount 0 le {exit} if } loop } def /miscHeights { /encoding fontdict /Encoding get def maketempfont % make real font defaultEncoding begin currentdict /H known {H nbbox (CapHeight ) print dup = nl 4p} {(CapHeight ) print BBury = nl} ifelse currentdict /x known {x nbbox (XHeight ) print dup = nl 4p} if currentdict /d known {d nbbox (Ascender ) print dup = nl 4p} if currentdict /p known {p nbbox (Descender ) print 2 index = nl 4p} if end } def /4p {pop pop pop pop} def /nbbox {char exch 0 exch put charbbox} def /charbbox { newpath 0 0 moveto char true charpath flattenpath pathbbox 4 {4 1 roll round cvi} repeat } def /char ( ) def /getcharmetric { /n exch def % grab the character code char 0 n put % make a string from it /label encoding n get def % record its text name (C ) print defaultEncoding label known {defaultEncoding label get} {-1} ifelse = ( ; ) print char stringwidth round cvi /ywidth exch def round cvi /xwidth exch def ywidth 0 eq {(WX ) print xwidth = } {(W ) print xwidth = sp ywidth =} ifelse ( ; N ) print label = ( ; B) print charbbox dup 3 index eq 2 index 5 index eq and {pop pop pop pop 0 0 0 0} if 4 copy ury max /ury xdef urx max /urx xdef lly min /lly xdef llx min /llx xdef 4 2 roll 2 {exch sp = sp =} repeat label /f eq {fontdict /CharStrings known {fontdict /CharStrings get dup /fi known {( ; L i fi) print} if /fl known {( ; L l fl) print} if } if } if ( ;) print nl } def %end /fontlist [] def /FontDirectoryKnown FontDirectory dup length 20 add dict copy def /appendnewfont { /fontlist [ fontlist aload pop FontDirectoryKnown begin FontDirectory {FontDirectoryKnown 2 index known {pop pop} {2 copy def pop} ifelse } forall end ] def } def /fontname {fontlist 0 get} def