Virtual fonts

Why virtual fonts?


We have already described how to use font re-encoding to turn an existing postscript font into a TeX font (.tfm file) with a differenct character ordering. This is very useful technique, because it allows us to always use the same encoding definitions within LaTeX, even when the character ordering used in the underlying postscript fonts varies.

This is not, however, the whole story. TeX, for instance, has the nice ability to automaticly substitute the ff-ligature for the letter combination ff in a word like fluff; we saw how to instruct TeX which ligature substitutions to make while preparing a .tfm file earlier. In most postscript font sets, however, such ligatures exist only in a seperate "expert" font. With our present techniques, which allow one set of ligature substitution commands per font, we cannot typeset fluff appropriately except with a line like:

 flu{\fontseries{e}\selectfont{ff}}
Ugh! The are other, similiar problems; for instance: many small caps sets unfortunately include only small caps, so that \textsc{Small Caps} produces SMALL CAPS instead of SMALL CAPS.

The solution to all such problems is simple: one must present TeX not just with a re-ordered real font but a "virtual" font, made up of the characters of several different real fonts.

Reading virtual property lists


Look at the textof the file garrm.vpl which we produced earlier. It should begin something like
(VTITLE Created by afm2tfm garrm.afm -v garrm.vpl -t T1.enc)
(COMMENT Please edit that VTITLE if you edit this file)
(FAMILY TeX-garrm)
(CODINGSCHEME AppleStandard + T1Encoding)
(DESIGNSIZE R 10.0)
(DESIGNUNITS R 1000)
(COMMENT DESIGNSIZE (1 em) IS IN POINTS)
(COMMENT OTHER DIMENSIONS ARE MULTIPLES OF DESIGNSIZE/1000)
(FONTDIMEN
   (SPACE D 250)
   (STRETCH D 200)
   (SHRINK D 100)
   (XHEIGHT D 425)
   (QUAD D 1000)
   (EXTRASPACE D 111)
   )
(MAPFONT D 0
   (FONTNAME garrm)
   )
 
This is a human-readable file describing the font garrm.tfm! After this introductry text there appears a LIGTABLE with entries like
(LIGTABLE
   (LABEL O 47) (comment quoteright)
   (LIG O 47 O 21) (comment quotedblright)
   (STOP)
   (LABEL C W)
   (KRN C a R -64)
   (STOP)
   )
This is a table of ligatures and kerns. The first three lines say that for character number 39 (octal number 47, the single right quote), a ligature is defined with itself such that, if it appears twice it is replaced by character number 17 (octal number 21, the doulbe right quote). This is a standard TeX ligature. The next three lines say that for the character W, a kerning pair is defined such that, if it is followed by the character a, they are moved 64 units closer together. After the LIGTABLE is a long list of entries like:
(CHARACTER O 377 (comment germandbls)
   (CHARWD R 548)
   (CHARHT R 721)
   (CHARDP R 13)
   (MAP
      (SETCHAR O 247)
      )
   )
This says that character number 255 (octal number 377, the german sz) has a certain width, height, and depth, and that it is formed by printing chracter 167 (octal 247) in font D 0. There is an entry like this for each character in the font.

Assembling virtual fonts


By editing this file before running vp2vf, we can change the font properties as read by TeX from the .tfm file produced. Let's add an ff-ligature to the font, which we will imagine is available in an expert set. Here are the steps: (1) Change the MAPFONT table to read
(MAPFONT D 0
   (FONTNAME garrm0)
   )
(MAPFONT D 1
   (FONTNAME garrm1)
   )
Now we can assemble the virtual font garrm from the real fonts garrm0 (the garamond roman postscript font) and garrm1 (the garamond expert postscript font). To obtain the accurate dimensions of the ff-ligature, one can run afm2tfm on the expert font, which will then have an entry like
(CHARACTER O 33) (comment ff)
   (CHARWD R 978)
   (CHARHT R 801)
   (MAP
      (SETCHAR O 14)
      )
   )
where we have supposed that the ff appears in position 12 (octal 14) of the expert font and that we are using the T1 encoding, which places ff in position 27 (octal 33) of the TeX font. Now we just paste the line
(CHARACTER O 33) (comment ff)
   (CHARWD R 978)
   (CHARHT R 801)
   (MAP
      (SELECTFONT D 1)
      (SETCHAR O 14)
      )
   )
into garrm.vpl. Note that we might have to replace some other description of character 27, which was left in by afm2tfm for lack of anything else to put there. This says that character 27 is formed by printing character 12 of font D 1, which is just what we want to do. Finally, we create an automatic ff ligature by adding
   (LABEL C f)
   (LIG C f O 33) (comment ff)
   (STOP)
to the LIGTABLE. That's it! When we run vf2vp, we obtain a .tfm file describing a virtual font that takes characters from two real fonts.

Using virtual fonts


TeX will happily compile a .dvi file using our virtual .tfm file, but we will not be able to print or view the .dvi file unless we tell the appropriate .dvi intrepreter how to get at the charaters of garrm0 and garrm1. For example, the psfonts.map file for dvips must now include the two lines
 garrm0 garrm0 "T1Encoding ReencodeFont" <T1.enc <garrm.pfa
 garrm1 garrm1 "T1Encoding ReencodeFont" <T1.enc <garex.pfa
in place of the single line for garrm used previously. Also, each dvi intrepreter must have access to the garrm.vf file produced by vp2vf in order to process the .dvi file properly.

The virtual font technique awakens the hope that one could construct very large (Unicode-sized) TeX fonts. Such fonts could be used to typeset essentially all languages with a roman-like script with the same encoding definitions. Unfortunately, TeX is limited internally to 256-character encoding vectors. Those interested in overcoming this limitation should look in to the Omega typesetting system; which is fully back-compatible with TeX and LaTeX but removes this limitation, as well as others.


Back to the table of contents, or... ...on to the overview