summaryrefslogtreecommitdiff
path: root/Master/tlpkg/tlgs/lib/pf2afm.ps
diff options
context:
space:
mode:
authorReinhard Kotucha <reinhard.kotucha@web.de>2010-05-12 19:25:45 +0000
committerReinhard Kotucha <reinhard.kotucha@web.de>2010-05-12 19:25:45 +0000
commitdc55d4f5cde421a3704c183bc6ceb3fcdb6b0653 (patch)
treedb0890c2f5f2714d527a42ad3fb7955ac5b1f545 /Master/tlpkg/tlgs/lib/pf2afm.ps
parent053ead4487e776b05721ec15b941fe0bc1b7d513 (diff)
tlgs: 8.70 => 8.71
git-svn-id: svn://tug.org/texlive/trunk@18215 c570f23f-e606-0410-a88d-b1316a301751
Diffstat (limited to 'Master/tlpkg/tlgs/lib/pf2afm.ps')
-rw-r--r--[-rwxr-xr-x]Master/tlpkg/tlgs/lib/pf2afm.ps1078
1 files changed, 539 insertions, 539 deletions
diff --git a/Master/tlpkg/tlgs/lib/pf2afm.ps b/Master/tlpkg/tlgs/lib/pf2afm.ps
index 3eb26f092d1..a79cb5b97cd 100755..100644
--- a/Master/tlpkg/tlgs/lib/pf2afm.ps
+++ b/Master/tlpkg/tlgs/lib/pf2afm.ps
@@ -1,539 +1,539 @@
-%!
-% This is a PostScript program for making an AFM file from
-% PFB / PFA and (optionally) PFM files.
-%
-% Written in BOP s.c., Gda\'nsk, Poland
-% e-mail contact: B.Jackowski@GUST.ORG.PL
-% version 0.5 (18 XII 1997)
-% version 0.55 (11 III 1998) -- unlimited number of chars in a font
-% version 1.00 (27 III 1998) -- scanning PFM subdirectory added,
-% code improved; version sent to LPD
-% version 1.01 (1 II 2000) -- message changed
-
-% Usage:
-% gs [-dNODISPLAY] -- pf2afm.ps disk_font_name
-%
-% The result is written to the file disk_font_name.afm, provided such
-% a file does not exist; otherwise program quits.
-%
-% The font can be either *.pfa or *.pfb; if no extension is supplied,
-% first disk_font_name.pfb is examined, then disk_font_name.pfa.
-% Moreover, if there is a *.pfm file in the same directory or in the
-% subdirectory PFM, i.e., disk_font_name.pfm or PFM/disk_font_name.pfm,
-% kern pairs from it are extracted, as well as additional font
-% parameters, usually absent from Type 1 fonts.
-
-% Tribute:
-% $Id: pf2afm.ps 9792 2009-06-13 14:33:18Z alexcher $
-% The program is based on James Clark's <jjc@jclark.uucp> printafm.ps
-% (with alterations by d.love@dl.ac.uk and L. Peter Deutsch) from
-% Ghostscript 5.10 distribution.
-
-/onechar 1 string def
-/edef {exch def} def
-/WinAnsiEncoding dup /Encoding findresource def
-
-% charnumber print-charname -
-% prints the name of the encoded character
-/print-charname {
- PFMCharSet 0 eq {
- WinAnsiEncoding
- } {
- PFBencoding
- } ifelse
- exch get =string cvs dup
- (.notdef) eq {
- /was.notdef true def
- } if
- print.to.ofi ( ) print.to.ofi
-} def
-
-/printquit {print flush quit} def
-
-% redirecting GS output to ``ofi'' file
-/eolch (\r\n) def
-/=only.to.ofi {ofi exch write=only} def % replaces GS's `=only'
-/print.to.ofi {ofi exch writestring} def % replaces `print'
-/=to.ofi { =only.to.ofi eolch print.to.ofi } def % replaces `='
-
-% read and skip: byte, short, word, double and long
-/readb-p {currPFMfile read not {(Unexpected EOF\n) printquit} if} def
-/readw-p {readb-p readb-p 256 mul add} def
-/reads-p {readw-p dup 32768 ge {65536 sub} if} def
-/readd-p {readb-p readb-p readb-p readb-p 256 mul add 256 mul add 256 mul add} def
-/readl-p /readd-p load def % double word is, in fact, long integer in GS
-/skipb-p {readb-p pop} def
-/skipw-p {skipb-p skipb-p} def
-/skips-p /skipw-p load def
-/skipd-p {skipb-p skipb-p skipb-p skipb-p} def
-/skipl-p /skipd-p load def
-/skipa-p { {skipb-p} repeat} def
-
-% PFMfile readPFMheader -
-% defines currPFMfile, PFMExtMetricOffset, PFMPairKernTableOffset
-
-/readPFMheader {
- currPFMfile bytesavailable
- % ---------------
- % PFM MAIN HEADER
- % ---------------
- skipw-p % PFM: version
- readd-p % PFM: size (size is dword, not word as the documentation says)
- ne {(Wrong file size\n) printquit} if
- 60 skipa-p % PFM: copyright
- skipw-p % PFM: Type
- skipw-p % PFM: Points
- skipw-p % PFM: VertRes
- skipw-p % PFM: HorizRes
- skipw-p % PFM: Ascent
- skipw-p % PFM: InternalLeading
- skipw-p % PFM: ExternalLeading
- skipb-p % PFM: Italic
- skipb-p % PFM: Underline
- skipb-p % PFM: Stikeout
- skipw-p % PFM: Weight
- readb-p % PFM: CharSet
- /PFMCharSet edef
- skipw-p % PFM: PixWidth
- skipw-p % PFM: PixHeight
- skipb-p % PFM: PitchAndFamily
- skipw-p % PFM: AvgWidth
- skipw-p % PFM: MaxWidth
- skipb-p % PFM: FirstChar
- skipb-p % PFM: LastChar
- skipb-p % PFM: DefaultChar
- skipb-p % PFM: BreakChar
- skipw-p % PFM: WidthBytes
- skipd-p % PFM: Device
- skipd-p % PFM: Face
- skipd-p % PFM: BitsPointer
- skipd-p % PFM: BitsOffset
- % here we assume that it is a PostScript font, i.e., it always uses
- % the extended width table, therefore the normal width table is empty
- % -------------
- % PFM EXTENSION
- % -------------
- skipw-p % PFMEX: SizeFields
- readd-p % PFMEX: ExtMetricOffset
- /PFMExtMetricOffset edef
- skipd-p % PFMEX: ExtentTable
- skipd-p % PFMEX: OriginTable
- readd-p % PFMEX: PairKernTable
- /PFMPairKernTableOffset edef
- skipd-p % PFMEX: TrackKernTable
- skipd-p % PFMEX: DriverInfo
- skipd-p % PFMEX: Reserved
-} def
-
-% requires that currPFMfile, PFMExtMetricOffset are defined
-% readPFMExtMetric -
-% defines PFMNumberofKernPairs
-
-/readPFMExtMetric {
- currPFMfile PFMExtMetricOffset setfileposition
- skips-p % EXTT: Size
- skips-p % EXTT: PointSize
- skips-p % EXTT: Orientation
- skips-p % EXTT: MasterHeight
- skips-p % EXTT: MinScale
- skips-p % EXTT: MaxScale
- skips-p % EXTT: MasterUnit
- reads-p % EXTT: CapHeight
- /PFMCapHeight edef
- reads-p % EXTT: XHeight
- /PFMXHeight edef
- reads-p % EXTT: LowerCaseAscent
- /PFMLowerCaseAscent edef
- reads-p % EXTT: LowerCaseDescent
- neg /PFMLowerCaseDescent edef
- skips-p % EXTT: Slant
- skips-p % EXTT: SuperScript
- skips-p % EXTT: SubScript
- skips-p % EXTT: SuperScriptSize
- skips-p % EXTT: SubScriptSize
- skips-p % EXTT: UnderlineOffset
- skips-p % EXTT: UnderlineWidth
- skips-p % EXTT: DoubleUpperUnderlineOffset
- skips-p % EXTT: DoubleLowerUnderlineOffset
- skips-p % EXTT: DoubleUpperUnderlineWidth
- skips-p % EXTT: DoubleLowerUnderlineWidth
- skips-p % EXTT: StrikeOutOffset
- skips-p % EXTT: StrikeOutWidth
- readw-p % EXTT: KernPairs
- /PFMNumberofKernPairs edef
- skipw-p % EXTT: KernTracks
-} def
-
-% requires that currPFMfile, PFMPairKernTableOffset, PFMNumberofKernPairs are defined
-% readPFMExtMetric -
-% prints kern pairs table in the AFM format
-
-/readPFMKernPairs {
- currPFMfile () ne {
- PFMdict begin
- PFMPairKernTableOffset 0 ne {
- currPFMfile PFMPairKernTableOffset setfileposition
- readw-p % undocumented kern count (although all remaining structures are
- % explicitly preceded by their sizes); if it were a stable
- % feature, EXTTEXTMETRICS could be skipped
- PFMNumberofKernPairs
-% 2 copy = =
- ne {
- (Inconsistent number of kern pairs\n) printquit
- } if
- (StartKernData) =to.ofi
- (StartKernPairs ) print.to.ofi
- PFMNumberofKernPairs =to.ofi
- % ---------
- % MAIN LOOP
- % ---------
- /was.notdef false def
- PFMNumberofKernPairs {
- (KPX ) print.to.ofi
- readb-p % first char
- print-charname
- readb-p % second char
- print-charname
- reads-p % kern amount
- =to.ofi
- } repeat
- was.notdef {
- (.notdef character ocurred among kern pairs) =
- (you'd better check the resulting AFM file.) =
- } if
- (EndKernPairs) =to.ofi
- (EndKernData) =to.ofi
- } if
- end
- } if
-} def
-
-% alias (for ``compatibility'' with J. Clark):
-/printkernpairs /readPFMKernPairs load def
-
-% printcharmetrics -
-
-/printcharmetrics {
- (StartCharMetrics ) print.to.ofi
- /PFBencoding currfont /Encoding get dup length array copy def
- /PFBcharstrings currfont /CharStrings get def
- PFBcharstrings length
- PFBcharstrings /.notdef known { 1 sub } if =to.ofi
- currfont 1000 scalefont setfont
- % checking Encoding array and CharStrings dictionary for
- % the consistency of names
- /was.inconsitent false def
- 0 1 255 {
- dup PFBencoding exch get
- PFBcharstrings exch known {
- pop
- }{
-% dup PFBencoding exch get =
- PFBencoding exch /.notdef put % fix Encoding array
- /was.inconsitent true def
- } ifelse
- } for
- was.inconsitent {
- (Encoding array contains name(s) absent from CharStrings dictionary) =
- } if
- % print metric data for each character in PFB encoding vector
- 0 1 255 {
- dup PFBencoding exch get
- dup /.notdef ne {
- exch dup printmetric
- }{
- pop pop
- } ifelse
- } for
- % xPFBencoding contains an entry for each name in the original
- % encoding vector
- /xPFBencoding PFBcharstrings length dict def
- PFBencoding {
- xPFBencoding exch true put
- } forall
-
- /fontiter 0 def
- /TMPFontTemplate (TMP_FONT#000) def
- {
- % NewPFBencoding is the new encoding vector
- /NewPFBencoding 256 array def
- 0 1 255 {
- NewPFBencoding exch /.notdef put
- } for
- % fill up NewPFBencoding with names from CharStrings dictionary that
- % are not encoded so far
- /i 0 def
- PFBcharstrings {
- pop
- i 255 le {
- dup xPFBencoding exch known not {
- dup xPFBencoding exch true put
- NewPFBencoding i 3 -1 roll put
- /i i 1 add def
- }{
- pop
- } ifelse
- }{
- pop exit
- } ifelse
- } forall
- i 0 eq {exit} if
- % define a new font with NewPFBencoding as its encoding vector
- currfont maxlength dict /NewTMPfont edef
- currfont {
- exch dup dup /FID ne exch /Encoding ne and {
- exch NewTMPfont 3 1 roll put
- }{
- pop pop
- } ifelse
- } forall
- % compute a unique name for a font to be registered
- /fontiter fontiter 1 add def
- TMPFontTemplate fontiter (000) cvs
- dup length TMPFontTemplate length exch sub exch putinterval
- /TMPFontName TMPFontTemplate cvn def
- NewTMPfont /FontName TMPFontName put
- NewTMPfont /Encoding NewPFBencoding put
- % make this new font the current font
- TMPFontName NewTMPfont definefont 1000 scalefont setfont
- % print metric data for each character in the newly created encoding vector
- 0 1 255 {
- dup NewPFBencoding exch get
- dup /.notdef ne {
- exch -1 printmetric
- }{
- pop pop exit
- } ifelse
- } for
- i 255 lt {exit} if
- } loop
- (EndCharMetrics) =to.ofi
-} def
-
-% name actual_code normal_code printmetric -
-
-/printmetric {
- (C ) print.to.ofi =only.to.ofi
- ( ; WX ) print.to.ofi
- onechar 0 3 -1 roll put
- onechar stringwidth pop round cvi =only.to.ofi
- ( ; N ) print.to.ofi =only.to.ofi
- ( ; B ) print.to.ofi
- newpath 0 0 moveto
- onechar false charpath flattenpath pathbbox
- newpath
- round cvi /ury edef round cvi /urx edef
- round cvi /lly edef round cvi /llx edef
- ury lly eq {/ury 0 def /lly 0 def} if % normalize degenrated BB
- urx llx eq {/urx 0 def /llx 0 def} if %
- llx =only.to.ofi ( ) print.to.ofi lly =only.to.ofi ( ) print.to.ofi
- urx =only.to.ofi ( ) print.to.ofi ury =only.to.ofi ( ) print.to.ofi
- (;) =to.ofi
-} def
-
-/printinfoitem {
- 3 1 roll 2 copy known {
- get dup type /stringtype ne { =string cvs } if exch
- print.to.ofi ( ) print.to.ofi =to.ofi
- }{
- pop pop pop
- } ifelse
-} def
-
-/printfontinfo {
- (Comment AFM Generated by Ghostscript/pf2afm) =to.ofi
- currfont /FontName (FontName) printinfoitem
- %
- currfont /FontInfo get
- dup /FullName (FullName) printinfoitem
- dup /FamilyName (FamilyName) printinfoitem
- dup /Weight (Weight) printinfoitem
- dup /Notice (Notice) printinfoitem
- dup /ItalicAngle (ItalicAngle) printinfoitem
- dup /isFixedPitch (IsFixedPitch) printinfoitem
- dup /UnderlinePosition (UnderlinePosition) printinfoitem
- dup /UnderlineThickness (UnderlineThickness) printinfoitem
- /version (Version) printinfoitem
- %
- (EncodingScheme FontSpecific) =to.ofi
- %
- (FontBBox) print.to.ofi
- currfont /FontBBox get {
- ( ) print.to.ofi round cvi =only.to.ofi
- } forall
- eolch print.to.ofi
- %
- currPFMfile () ne {
- PFMdict
- dup /PFMCapHeight (CapHeight) printinfoitem
- dup /PFMXHeight (XHeight) printinfoitem
- dup /PFMLowerCaseDescent (Descender) printinfoitem
- /PFMLowerCaseAscent (Ascender) printinfoitem
- } if
-} def
-
-/readPFBfile {
- % make a shot of the actual font directory:
- /oldFontDirectory FontDirectory dup length dict copy def
- isPFB {% defined in `makeafm'
- (r) file true /PFBDecode filter cvx % true is better (see gs_type1.ps)
- mark exch exec
- }{
- (r) file mark exch run
- } ifelse
- cleartomark
- % make a shot of the updated font directory:
- /newFontDirectory FontDirectory dup length dict copy def
- % spot the added font:
- oldFontDirectory {pop newFontDirectory exch undef} forall
- newFontDirectory length 1 ne {
- newFontDirectory length =
- (Weird PFB file?\n) printquit
- } if
- newFontDirectory {pop} forall
- findfont /currfont edef
-} def
-
-/readPFMfile {
- dup () ne {
- (r) file /currPFMfile edef
- 10 dict dup /PFMdict edef begin
- readPFMheader
- readPFMExtMetric
- end
- }{
- pop /currPFMfile () def
- } ifelse
-} def
-
-% pfmfilename pf[ba]filename filetype printafm -
-% where filetype=(a) or (b)
-
-/printafm {
- readPFBfile
- readPFMfile
- (StartFontMetrics 2.0) =to.ofi
- printfontinfo
- printcharmetrics
- printkernpairs
- (EndFontMetrics) =to.ofi
-} def
-
-/pfa_pfb_dict <<
- /.pfb /pfbn
- /.pfB /pfbn
- /.pFb /pfbn
- /.pFB /pfbn
- /.Pfb /pfbn
- /.PfB /pfbn
- /.PFb /pfbn
- /.PFB /pfbn
-
- /.pfa /pfan
- /.pfA /pfan
- /.pFa /pfan
- /.pFA /pfan
- /.Pfa /pfan
- /.PfA /pfan
- /.PFa /pfan
- /.PFA /pfan
->> readonly def
-
-% Check whether the file name has pfa or pfb extension.
-/pfa_or_pfb? { % s -> false | /name true
- dup length 4 lt {
- pop //false
- } {
- dup length 4 sub 4 getinterval //pfa_pfb_dict exch .knownget
- } ifelse
-} bind def
-
-
-% pf[ba]filename makeafm -
-/makeafm {
- count 0 eq {(Missing font file name\n) printquit} if
- /ifn edef
- ifn length 0 eq {(Empty font file name\n) printquit} if
-% the following piece of the code does, in fact, the job of a system shell,
-% i.e., it analyses the supplied names, appends extensions if needed,
-% and check files:
- /pfbn () def /pfan () def /pfmn () def % initialisation
- [ t1_glyph_equivalence { pop } forall ] { % disable glyph substitution
- t1_glyph_equivalence exch undef
- } forall
- ifn pfa_or_pfb? {
- ifn dup length string copy def
- ifn dup length 4 sub 0 exch getinterval /ifn edef
- } if
- pfbn () eq pfan () eq and dup {% no extension was supplied, try ".pfb"
- /pfbn ifn (.pfb) concatstrings def
- } if
- pfbn () ne {% check whether "filename.pfb" exists
- pfbn status {pop pop pop pop /isPFB true def}{/pfbn () def} ifelse
- } if
- pfbn () eq and {% checking "filename.pfb" unsuccessful, try ".pfa"
- /pfan ifn (.pfa) concatstrings def
- } if
- pfan () ne {% check whether "filename.pfa" exists
- pfan status {pop pop pop pop /isPFB false def}{/pfan () def} ifelse
- } if
-
- pfbn () eq pfan () eq and {
- (Neither pfa nor pfb found\n) printquit
- } if
-
- /ofn ifn (.afm) concatstrings def
- ofn status {
- pop pop pop pop (Resulting file exists\n) printquit
- } if
- /ofi ofn (w) file def
-
- /pfmn ifn (.pfm) concatstrings def
- pfmn status {
- pop pop pop pop
- }{
- () pfmn {
- (/) search dup not { pop (\\) search } if {
- 4 -1 roll exch concatstrings exch concatstrings exch
- }{
- exit
- } ifelse
- } loop
- (pfm/) exch concatstrings concatstrings
- dup status {
- pop pop pop pop /pfmn edef
- }{
- pop /pfmn () def (pfm file not found -- ignored\n) print
- } ifelse
- } ifelse
- //systemdict /.setsafe known {
- <<
- /PermitFileReading
- [ pfmn dup length 0 eq { pop } if
- isPFB {pfbn}{pfan} ifelse
- ]
- /PermitFileWriting [ ]
- /PermitFileControl [ ]
- >> setuserparams
- .locksafe
- } if
-
-
- pfmn
- isPFB {pfbn}{pfan} ifelse
- printafm
-
-} def
-
-% Check for command line arguments.
-[ shellarguments
- { ] dup length 1 eq {
- 0 get makeafm
- }{
- (This is PF2AFM -- AFM generator \(ver. 1.00\)\n) print
- (Usage: gs [-dNODISPLAY] -- pf2afm.ps disk_font_name\n) printquit
- } ifelse
- }
- {pop}
-ifelse
-
+%!
+% This is a PostScript program for making an AFM file from
+% PFB / PFA and (optionally) PFM files.
+%
+% Written in BOP s.c., Gda\'nsk, Poland
+% e-mail contact: B.Jackowski@GUST.ORG.PL
+% version 0.5 (18 XII 1997)
+% version 0.55 (11 III 1998) -- unlimited number of chars in a font
+% version 1.00 (27 III 1998) -- scanning PFM subdirectory added,
+% code improved; version sent to LPD
+% version 1.01 (1 II 2000) -- message changed
+
+% Usage:
+% gs [-dNODISPLAY] -- pf2afm.ps disk_font_name
+%
+% The result is written to the file disk_font_name.afm, provided such
+% a file does not exist; otherwise program quits.
+%
+% The font can be either *.pfa or *.pfb; if no extension is supplied,
+% first disk_font_name.pfb is examined, then disk_font_name.pfa.
+% Moreover, if there is a *.pfm file in the same directory or in the
+% subdirectory PFM, i.e., disk_font_name.pfm or PFM/disk_font_name.pfm,
+% kern pairs from it are extracted, as well as additional font
+% parameters, usually absent from Type 1 fonts.
+
+% Tribute:
+% $Id: pf2afm.ps 9792 2009-06-13 14:33:18Z alexcher $
+% The program is based on James Clark's <jjc@jclark.uucp> printafm.ps
+% (with alterations by d.love@dl.ac.uk and L. Peter Deutsch) from
+% Ghostscript 5.10 distribution.
+
+/onechar 1 string def
+/edef {exch def} def
+/WinAnsiEncoding dup /Encoding findresource def
+
+% charnumber print-charname -
+% prints the name of the encoded character
+/print-charname {
+ PFMCharSet 0 eq {
+ WinAnsiEncoding
+ } {
+ PFBencoding
+ } ifelse
+ exch get =string cvs dup
+ (.notdef) eq {
+ /was.notdef true def
+ } if
+ print.to.ofi ( ) print.to.ofi
+} def
+
+/printquit {print flush quit} def
+
+% redirecting GS output to ``ofi'' file
+/eolch (\r\n) def
+/=only.to.ofi {ofi exch write=only} def % replaces GS's `=only'
+/print.to.ofi {ofi exch writestring} def % replaces `print'
+/=to.ofi { =only.to.ofi eolch print.to.ofi } def % replaces `='
+
+% read and skip: byte, short, word, double and long
+/readb-p {currPFMfile read not {(Unexpected EOF\n) printquit} if} def
+/readw-p {readb-p readb-p 256 mul add} def
+/reads-p {readw-p dup 32768 ge {65536 sub} if} def
+/readd-p {readb-p readb-p readb-p readb-p 256 mul add 256 mul add 256 mul add} def
+/readl-p /readd-p load def % double word is, in fact, long integer in GS
+/skipb-p {readb-p pop} def
+/skipw-p {skipb-p skipb-p} def
+/skips-p /skipw-p load def
+/skipd-p {skipb-p skipb-p skipb-p skipb-p} def
+/skipl-p /skipd-p load def
+/skipa-p { {skipb-p} repeat} def
+
+% PFMfile readPFMheader -
+% defines currPFMfile, PFMExtMetricOffset, PFMPairKernTableOffset
+
+/readPFMheader {
+ currPFMfile bytesavailable
+ % ---------------
+ % PFM MAIN HEADER
+ % ---------------
+ skipw-p % PFM: version
+ readd-p % PFM: size (size is dword, not word as the documentation says)
+ ne {(Wrong file size\n) printquit} if
+ 60 skipa-p % PFM: copyright
+ skipw-p % PFM: Type
+ skipw-p % PFM: Points
+ skipw-p % PFM: VertRes
+ skipw-p % PFM: HorizRes
+ skipw-p % PFM: Ascent
+ skipw-p % PFM: InternalLeading
+ skipw-p % PFM: ExternalLeading
+ skipb-p % PFM: Italic
+ skipb-p % PFM: Underline
+ skipb-p % PFM: Stikeout
+ skipw-p % PFM: Weight
+ readb-p % PFM: CharSet
+ /PFMCharSet edef
+ skipw-p % PFM: PixWidth
+ skipw-p % PFM: PixHeight
+ skipb-p % PFM: PitchAndFamily
+ skipw-p % PFM: AvgWidth
+ skipw-p % PFM: MaxWidth
+ skipb-p % PFM: FirstChar
+ skipb-p % PFM: LastChar
+ skipb-p % PFM: DefaultChar
+ skipb-p % PFM: BreakChar
+ skipw-p % PFM: WidthBytes
+ skipd-p % PFM: Device
+ skipd-p % PFM: Face
+ skipd-p % PFM: BitsPointer
+ skipd-p % PFM: BitsOffset
+ % here we assume that it is a PostScript font, i.e., it always uses
+ % the extended width table, therefore the normal width table is empty
+ % -------------
+ % PFM EXTENSION
+ % -------------
+ skipw-p % PFMEX: SizeFields
+ readd-p % PFMEX: ExtMetricOffset
+ /PFMExtMetricOffset edef
+ skipd-p % PFMEX: ExtentTable
+ skipd-p % PFMEX: OriginTable
+ readd-p % PFMEX: PairKernTable
+ /PFMPairKernTableOffset edef
+ skipd-p % PFMEX: TrackKernTable
+ skipd-p % PFMEX: DriverInfo
+ skipd-p % PFMEX: Reserved
+} def
+
+% requires that currPFMfile, PFMExtMetricOffset are defined
+% readPFMExtMetric -
+% defines PFMNumberofKernPairs
+
+/readPFMExtMetric {
+ currPFMfile PFMExtMetricOffset setfileposition
+ skips-p % EXTT: Size
+ skips-p % EXTT: PointSize
+ skips-p % EXTT: Orientation
+ skips-p % EXTT: MasterHeight
+ skips-p % EXTT: MinScale
+ skips-p % EXTT: MaxScale
+ skips-p % EXTT: MasterUnit
+ reads-p % EXTT: CapHeight
+ /PFMCapHeight edef
+ reads-p % EXTT: XHeight
+ /PFMXHeight edef
+ reads-p % EXTT: LowerCaseAscent
+ /PFMLowerCaseAscent edef
+ reads-p % EXTT: LowerCaseDescent
+ neg /PFMLowerCaseDescent edef
+ skips-p % EXTT: Slant
+ skips-p % EXTT: SuperScript
+ skips-p % EXTT: SubScript
+ skips-p % EXTT: SuperScriptSize
+ skips-p % EXTT: SubScriptSize
+ skips-p % EXTT: UnderlineOffset
+ skips-p % EXTT: UnderlineWidth
+ skips-p % EXTT: DoubleUpperUnderlineOffset
+ skips-p % EXTT: DoubleLowerUnderlineOffset
+ skips-p % EXTT: DoubleUpperUnderlineWidth
+ skips-p % EXTT: DoubleLowerUnderlineWidth
+ skips-p % EXTT: StrikeOutOffset
+ skips-p % EXTT: StrikeOutWidth
+ readw-p % EXTT: KernPairs
+ /PFMNumberofKernPairs edef
+ skipw-p % EXTT: KernTracks
+} def
+
+% requires that currPFMfile, PFMPairKernTableOffset, PFMNumberofKernPairs are defined
+% readPFMExtMetric -
+% prints kern pairs table in the AFM format
+
+/readPFMKernPairs {
+ currPFMfile () ne {
+ PFMdict begin
+ PFMPairKernTableOffset 0 ne {
+ currPFMfile PFMPairKernTableOffset setfileposition
+ readw-p % undocumented kern count (although all remaining structures are
+ % explicitly preceded by their sizes); if it were a stable
+ % feature, EXTTEXTMETRICS could be skipped
+ PFMNumberofKernPairs
+% 2 copy = =
+ ne {
+ (Inconsistent number of kern pairs\n) printquit
+ } if
+ (StartKernData) =to.ofi
+ (StartKernPairs ) print.to.ofi
+ PFMNumberofKernPairs =to.ofi
+ % ---------
+ % MAIN LOOP
+ % ---------
+ /was.notdef false def
+ PFMNumberofKernPairs {
+ (KPX ) print.to.ofi
+ readb-p % first char
+ print-charname
+ readb-p % second char
+ print-charname
+ reads-p % kern amount
+ =to.ofi
+ } repeat
+ was.notdef {
+ (.notdef character ocurred among kern pairs) =
+ (you'd better check the resulting AFM file.) =
+ } if
+ (EndKernPairs) =to.ofi
+ (EndKernData) =to.ofi
+ } if
+ end
+ } if
+} def
+
+% alias (for ``compatibility'' with J. Clark):
+/printkernpairs /readPFMKernPairs load def
+
+% printcharmetrics -
+
+/printcharmetrics {
+ (StartCharMetrics ) print.to.ofi
+ /PFBencoding currfont /Encoding get dup length array copy def
+ /PFBcharstrings currfont /CharStrings get def
+ PFBcharstrings length
+ PFBcharstrings /.notdef known { 1 sub } if =to.ofi
+ currfont 1000 scalefont setfont
+ % checking Encoding array and CharStrings dictionary for
+ % the consistency of names
+ /was.inconsitent false def
+ 0 1 255 {
+ dup PFBencoding exch get
+ PFBcharstrings exch known {
+ pop
+ }{
+% dup PFBencoding exch get =
+ PFBencoding exch /.notdef put % fix Encoding array
+ /was.inconsitent true def
+ } ifelse
+ } for
+ was.inconsitent {
+ (Encoding array contains name(s) absent from CharStrings dictionary) =
+ } if
+ % print metric data for each character in PFB encoding vector
+ 0 1 255 {
+ dup PFBencoding exch get
+ dup /.notdef ne {
+ exch dup printmetric
+ }{
+ pop pop
+ } ifelse
+ } for
+ % xPFBencoding contains an entry for each name in the original
+ % encoding vector
+ /xPFBencoding PFBcharstrings length dict def
+ PFBencoding {
+ xPFBencoding exch true put
+ } forall
+
+ /fontiter 0 def
+ /TMPFontTemplate (TMP_FONT#000) def
+ {
+ % NewPFBencoding is the new encoding vector
+ /NewPFBencoding 256 array def
+ 0 1 255 {
+ NewPFBencoding exch /.notdef put
+ } for
+ % fill up NewPFBencoding with names from CharStrings dictionary that
+ % are not encoded so far
+ /i 0 def
+ PFBcharstrings {
+ pop
+ i 255 le {
+ dup xPFBencoding exch known not {
+ dup xPFBencoding exch true put
+ NewPFBencoding i 3 -1 roll put
+ /i i 1 add def
+ }{
+ pop
+ } ifelse
+ }{
+ pop exit
+ } ifelse
+ } forall
+ i 0 eq {exit} if
+ % define a new font with NewPFBencoding as its encoding vector
+ currfont maxlength dict /NewTMPfont edef
+ currfont {
+ exch dup dup /FID ne exch /Encoding ne and {
+ exch NewTMPfont 3 1 roll put
+ }{
+ pop pop
+ } ifelse
+ } forall
+ % compute a unique name for a font to be registered
+ /fontiter fontiter 1 add def
+ TMPFontTemplate fontiter (000) cvs
+ dup length TMPFontTemplate length exch sub exch putinterval
+ /TMPFontName TMPFontTemplate cvn def
+ NewTMPfont /FontName TMPFontName put
+ NewTMPfont /Encoding NewPFBencoding put
+ % make this new font the current font
+ TMPFontName NewTMPfont definefont 1000 scalefont setfont
+ % print metric data for each character in the newly created encoding vector
+ 0 1 255 {
+ dup NewPFBencoding exch get
+ dup /.notdef ne {
+ exch -1 printmetric
+ }{
+ pop pop exit
+ } ifelse
+ } for
+ i 255 lt {exit} if
+ } loop
+ (EndCharMetrics) =to.ofi
+} def
+
+% name actual_code normal_code printmetric -
+
+/printmetric {
+ (C ) print.to.ofi =only.to.ofi
+ ( ; WX ) print.to.ofi
+ onechar 0 3 -1 roll put
+ onechar stringwidth pop round cvi =only.to.ofi
+ ( ; N ) print.to.ofi =only.to.ofi
+ ( ; B ) print.to.ofi
+ newpath 0 0 moveto
+ onechar false charpath flattenpath pathbbox
+ newpath
+ round cvi /ury edef round cvi /urx edef
+ round cvi /lly edef round cvi /llx edef
+ ury lly eq {/ury 0 def /lly 0 def} if % normalize degenrated BB
+ urx llx eq {/urx 0 def /llx 0 def} if %
+ llx =only.to.ofi ( ) print.to.ofi lly =only.to.ofi ( ) print.to.ofi
+ urx =only.to.ofi ( ) print.to.ofi ury =only.to.ofi ( ) print.to.ofi
+ (;) =to.ofi
+} def
+
+/printinfoitem {
+ 3 1 roll 2 copy known {
+ get dup type /stringtype ne { =string cvs } if exch
+ print.to.ofi ( ) print.to.ofi =to.ofi
+ }{
+ pop pop pop
+ } ifelse
+} def
+
+/printfontinfo {
+ (Comment AFM Generated by Ghostscript/pf2afm) =to.ofi
+ currfont /FontName (FontName) printinfoitem
+ %
+ currfont /FontInfo get
+ dup /FullName (FullName) printinfoitem
+ dup /FamilyName (FamilyName) printinfoitem
+ dup /Weight (Weight) printinfoitem
+ dup /Notice (Notice) printinfoitem
+ dup /ItalicAngle (ItalicAngle) printinfoitem
+ dup /isFixedPitch (IsFixedPitch) printinfoitem
+ dup /UnderlinePosition (UnderlinePosition) printinfoitem
+ dup /UnderlineThickness (UnderlineThickness) printinfoitem
+ /version (Version) printinfoitem
+ %
+ (EncodingScheme FontSpecific) =to.ofi
+ %
+ (FontBBox) print.to.ofi
+ currfont /FontBBox get {
+ ( ) print.to.ofi round cvi =only.to.ofi
+ } forall
+ eolch print.to.ofi
+ %
+ currPFMfile () ne {
+ PFMdict
+ dup /PFMCapHeight (CapHeight) printinfoitem
+ dup /PFMXHeight (XHeight) printinfoitem
+ dup /PFMLowerCaseDescent (Descender) printinfoitem
+ /PFMLowerCaseAscent (Ascender) printinfoitem
+ } if
+} def
+
+/readPFBfile {
+ % make a shot of the actual font directory:
+ /oldFontDirectory FontDirectory dup length dict copy def
+ isPFB {% defined in `makeafm'
+ (r) file true /PFBDecode filter cvx % true is better (see gs_type1.ps)
+ mark exch exec
+ }{
+ (r) file mark exch run
+ } ifelse
+ cleartomark
+ % make a shot of the updated font directory:
+ /newFontDirectory FontDirectory dup length dict copy def
+ % spot the added font:
+ oldFontDirectory {pop newFontDirectory exch undef} forall
+ newFontDirectory length 1 ne {
+ newFontDirectory length =
+ (Weird PFB file?\n) printquit
+ } if
+ newFontDirectory {pop} forall
+ findfont /currfont edef
+} def
+
+/readPFMfile {
+ dup () ne {
+ (r) file /currPFMfile edef
+ 10 dict dup /PFMdict edef begin
+ readPFMheader
+ readPFMExtMetric
+ end
+ }{
+ pop /currPFMfile () def
+ } ifelse
+} def
+
+% pfmfilename pf[ba]filename filetype printafm -
+% where filetype=(a) or (b)
+
+/printafm {
+ readPFBfile
+ readPFMfile
+ (StartFontMetrics 2.0) =to.ofi
+ printfontinfo
+ printcharmetrics
+ printkernpairs
+ (EndFontMetrics) =to.ofi
+} def
+
+/pfa_pfb_dict <<
+ /.pfb /pfbn
+ /.pfB /pfbn
+ /.pFb /pfbn
+ /.pFB /pfbn
+ /.Pfb /pfbn
+ /.PfB /pfbn
+ /.PFb /pfbn
+ /.PFB /pfbn
+
+ /.pfa /pfan
+ /.pfA /pfan
+ /.pFa /pfan
+ /.pFA /pfan
+ /.Pfa /pfan
+ /.PfA /pfan
+ /.PFa /pfan
+ /.PFA /pfan
+>> readonly def
+
+% Check whether the file name has pfa or pfb extension.
+/pfa_or_pfb? { % s -> false | /name true
+ dup length 4 lt {
+ pop //false
+ } {
+ dup length 4 sub 4 getinterval //pfa_pfb_dict exch .knownget
+ } ifelse
+} bind def
+
+
+% pf[ba]filename makeafm -
+/makeafm {
+ count 0 eq {(Missing font file name\n) printquit} if
+ /ifn edef
+ ifn length 0 eq {(Empty font file name\n) printquit} if
+% the following piece of the code does, in fact, the job of a system shell,
+% i.e., it analyses the supplied names, appends extensions if needed,
+% and check files:
+ /pfbn () def /pfan () def /pfmn () def % initialisation
+ [ t1_glyph_equivalence { pop } forall ] { % disable glyph substitution
+ t1_glyph_equivalence exch undef
+ } forall
+ ifn pfa_or_pfb? {
+ ifn dup length string copy def
+ ifn dup length 4 sub 0 exch getinterval /ifn edef
+ } if
+ pfbn () eq pfan () eq and dup {% no extension was supplied, try ".pfb"
+ /pfbn ifn (.pfb) concatstrings def
+ } if
+ pfbn () ne {% check whether "filename.pfb" exists
+ pfbn status {pop pop pop pop /isPFB true def}{/pfbn () def} ifelse
+ } if
+ pfbn () eq and {% checking "filename.pfb" unsuccessful, try ".pfa"
+ /pfan ifn (.pfa) concatstrings def
+ } if
+ pfan () ne {% check whether "filename.pfa" exists
+ pfan status {pop pop pop pop /isPFB false def}{/pfan () def} ifelse
+ } if
+
+ pfbn () eq pfan () eq and {
+ (Neither pfa nor pfb found\n) printquit
+ } if
+
+ /ofn ifn (.afm) concatstrings def
+ ofn status {
+ pop pop pop pop (Resulting file exists\n) printquit
+ } if
+ /ofi ofn (w) file def
+
+ /pfmn ifn (.pfm) concatstrings def
+ pfmn status {
+ pop pop pop pop
+ }{
+ () pfmn {
+ (/) search dup not { pop (\\) search } if {
+ 4 -1 roll exch concatstrings exch concatstrings exch
+ }{
+ exit
+ } ifelse
+ } loop
+ (pfm/) exch concatstrings concatstrings
+ dup status {
+ pop pop pop pop /pfmn edef
+ }{
+ pop /pfmn () def (pfm file not found -- ignored\n) print
+ } ifelse
+ } ifelse
+ //systemdict /.setsafe known {
+ <<
+ /PermitFileReading
+ [ pfmn dup length 0 eq { pop } if
+ isPFB {pfbn}{pfan} ifelse
+ ]
+ /PermitFileWriting [ ]
+ /PermitFileControl [ ]
+ >> setuserparams
+ .locksafe
+ } if
+
+
+ pfmn
+ isPFB {pfbn}{pfan} ifelse
+ printafm
+
+} def
+
+% Check for command line arguments.
+[ shellarguments
+ { ] dup length 1 eq {
+ 0 get makeafm
+ }{
+ (This is PF2AFM -- AFM generator \(ver. 1.00\)\n) print
+ (Usage: gs [-dNODISPLAY] -- pf2afm.ps disk_font_name\n) printquit
+ } ifelse
+ }
+ {pop}
+ifelse
+