<html><head><meta name="color-scheme" content="light dark"></head><body><pre style="word-wrap: break-word; white-space: pre-wrap;">
\begingroup\let\ref\relax

\let\bfsl\sl%\newcommand{\bfsl}{\series{bx}\sl}
\def\ritem[#1]{\par\hangindent\parindent{\noindent\bf #1}\enspace}
\def\SliTeXb{{\bf S{\scb LI}\TeX}}

\title{A Script for building true-sized fonts}
This article is about creating John~Sauter's reworking of the Computer Modern
fonts (see `How well do you know your CM fonts?' by Sebastian Rahtz,
in \TeXline~9). We have been using Sauter's CM fonts in the Computer Science
Department at Edinburgh University for over a year now, mainly in conjunction
with \LaTeX{} (built on top of \TeX~2.97, and latterly \TeX~2.991 and
\TeX~3.0).

The process of getting \LaTeX{} to work with Sauter's fonts was
rather tedious, involving editing {\tt lfonts.tex}, using \MF{} to create
{\tt gf} (Generic Font) format and {\tfm} (\TeX{} Font Metric) files,
converting the {\tt gf} files to the {\pk} (Packed Font) format used by our
printer driver, and building new format files for \LaTeX{} on each
architecture which we support (with the latest version of the {\tt web2c}
system for building \TeX, format files which do not contain |glue_ratio|
quantities may be shared across architectures; this includes plain \TeX\ and
\LaTeX\ formats. This article will concentrate on a {\unix} shell script to
assist with the second and third steps outlined above, but first I~will
present some background.

\section{Background}
I~decided to update our installation to \TeX~3, and aquire a
more recent version of \LaTeX{} than the one we were using. After a little bit
of investigation, I also decided to install Mittelbach and Sch\"opf's new font
selection scheme for \LaTeX{} (see Tugboat~10 no.1). This new scheme
provides a more flexible interface to fonts, allowing users to alter the {\em
family\/}, {\em series\/}, {\em shape\/}, and {\em size} of fonts
independently. Thus typing |\sl| while boldface is selected will choose
a{\bfsl slanted boldface\/} font if possible. There are also advantages in font
management, making it far easier to install new fonts (especially fonts which
are used in math mode), or change regular \LaTeX{} fonts for other fonts.

The Computer Science Department at Edinburgh has a large number
of theoreticians, who like to use as many wierd symbols as they can, so I~took
advantage of the new font selection scheme to install the AMS
(American Mathematical Society) math symbol fonts {\tt msxm} and {\tt msym} as
new math alphabets (I~have recently updated these to the new {\tt
msam} and {\tt msbm} fonts). The size of symbols is set by the normal
\LaTeX{} size-changing commands.

The department runs a network consisting of mainly Sun~3 and Sun~4
workstations, with a few other machines (Hewlett-Packard workstations and DEC
{\sc mips} workstations) connected. There are currently seven remotely
accessable laser printers, most of which are 300\,\dpi,  one of which is
400\,\dpi, and another which is switchable between 300 and 400\,\dpi. This
requires maintaining two complete sets of fonts, taking twice the disc space.
We also keep fonts at magnification 700 ($0.7$ normal size) for printing
two-up. We wanted a usable number of fonts without being constrained too
much, and without taking too much disc space.

\section{Font Requirements}
The new \LaTeX{} font selection scheme makes it much easier to access
fonts, so I~also decided to re-examine the fonts available, and build a
new set of fonts for use with it. I~categorised the Computer Modern
and other fonts which we have available into four groups:

\ritem[Text fonts] These are fonts which would probably be used in normal text.
\ritem[Math fonts] These are fonts which are normally accessed within math
mode.
\ritem[Special fonts] These fonts are usually explicitly loaded, and are not
required in a large range of sizes.
\ritem[\SliTeXb{} fonts] These are the extra fonts required to run \SliTeX{}
with true-sized fonts.

\noindent
Table~1 shows the sizes chosen for the first group of
fonts. Note that the fonts {\tt cmr}, {\tt cmss} and {\tt cmtt}
appear in all sizes from 5 to 25 points; these fonts correspond to the normal
series and shape of the font families defined by Mittelbach and Sch\"opf. When
a family\slash series\slash shape\slash size combination cannot be found, the
medium series and normal series and shape is substituted instead. The fonts
{\tt cmbx} and {\tt cmti} also appear in the full range of point sizes
because of their use in chapter and section headings. The sizes of the other
text fonts corresponds to the range |\footnotesize| in \LaTeX's 10~point
styles to |\Large| in 12~point styles. I~felt that this would be a large
enough range to satisfy most users, without taking up too much disc space.

\topinsert
\hsize6.5in
\raggedright\parindent0pt

\setbox0\vtop{%
\halign{\vtop{\hsize1.5in\strut#\strut}&amp;\vtop{\hsize1.5in\strut#\strut}\cr
\multispan2{\hfill\bf\strut Table 1: Sizes of `Text' fonts available\hfill}\cr
\noalign{\smallskip}
\noalign{\hrule}
Font &amp; Sizes available\cr
\noalign{\hrule}
cmbx, cmr, cmss, cmti, cmtt &amp; 5, 6, 7, 8, 9, 10, 11, 12, 14, 17, 20, 25\cr
\noalign{\hrule}
cmb, cmbxsl, cmbxti, cmcsc, cmitt, cmsl, cmssbx,
cmssdc, cmssi, cmtcsc, cmu, cmvtt &amp; 8, 9, 10, 11, 12, 14, 17\cr
\noalign{\hrule}
}}

\setbox1\vtop{%
\halign{\vtop{\hsize1.5in\strut#\strut}&amp;\vtop{\hsize1.5in\strut#\strut}\cr
\multispan2{\hfill\bf\strut Table 2: Sizes of `Math' fonts available\hfill}\cr
\noalign{\smallskip}
\noalign{\hrule}
Font &amp; Sizes available\cr
\noalign{\hrule}
cmmi, cmsy, lasy &amp; 5, 6, 7, 8, 9, 10, 11, 12, 14, 17, 20, 25\cr
\noalign{\hrule}
cmbsy, cmmib, lasyb &amp; 5, 6, 7, 8, 9, 10, 11, 12, 14, 17\cr
\noalign{\hrule}
}}

\line{\box0\hfill\box1}\bigskip
\hrule height1pt depth1pt
\bigskip
\endinsert


Table~2 gives the sizes in which the fonts used in math mode
were made available. These fonts will probably be used in sub-scripts,
super-scripts, and sub-sub-~(super-super)~scripts, so the sizes down to
|\scriptscriptsize| in 10~point styles were built. 




\setbox0\vbox{\raggedright\parindent0pt
\halign{\vbox{\hsize1.5in\strut#\strut}&amp;\vtop{\hsize1.5in\strut#\strut}\cr
\noalign{\hrule}
Font &amp; Sizes available\cr
\noalign{\hrule}
cmdunh, cmex cmff, cmfi, cmph, cmphi, cmtex,
lcircle, lcirclew, line, linew, logo, logobf, logosl, manfnt &amp; 10\cr
\noalign{\hrule}
cmfib, cmssq, cmssqi &amp; 8, 10\cr
\noalign{\hrule}
cminch &amp; 72.27\cr
\noalign{\hrule}
\noalign{\smallskip}
\multispan2{\hfill\bf\strut Table 3: Sizes of `Special' fonts available\hfill}\cr
}}

Table~3 shows the sizes at which the special fonts were
built. These fonts include some which are required for \LaTeX{} (for example,
{\tt cmex}, {\tt lcircle}, and {\tt line}), some interesting variants on
Computer Modern, and a few miscellaneous fonts.
\smallskip
\line{\box0}
\bigskip
\section{The {\ttit make\_font} script}
The |make_font| script described here was written for the C-shell. It is
used in conjunction with John Sauter's parameterised Computer Modern fonts,
available from the Aston archive in the directory
|[tex-archive.fonts.sauter]|. It is loosely based on several of
the shell scripts in that directory, but I~believe it is easier to use.
|make_font| creates a single font at several sizes, converts
the resulting {\tt gf} files to {\tt pk} files, and moves them to an
appropriate directory. The font organisation which we use in the
department keeps all of the fonts for each resolution in a directory called
{\tt /usr/local/share/tex/fonts/pk/}{\it device}{\tt/dpi}{\it res}, where {\it
device\/} is the device for which the fonts are to be used, and {\it res\/} is
the resolution of the fonts, in dots per inch. The fonts in these directories
are named {\it font}{\tt.pk}; the resolution is not part of the font
name. Only {\tt pk} fonts are used in the department. The {\tt make\_font}
script was written for this convention, but could easily be converted to other
conventions. Errors are logged on the standard output stream.

\setbox1\vtop{\raggedright\parindent0pt
\halign{\strut#\hfil &amp;\hfil#\,\dpi\hfil&amp;\quad\hfil#\quad&amp;\hfil#\quad\cr
Device &amp;\omit\hfil Resolution\hfil     &amp;\omit\quad\hfil 
Magnification\hfil&amp;\omit\hfil Size Kbytes\cr \noalign{\hrule}
Agfa&amp;400&amp;1000&amp;2863\cr
Agfa&amp;280&amp;700&amp;1990\cr
Canon&amp;300&amp;1000&amp;2310\cr
Canon&amp;210&amp;700&amp;1567\cr
\noalign{\hrule}
\noalign{\smallskip}
\multispan4{\hfill\bf\strut Table 4: Directory sizes 
for true-sized fonts\hfill}\cr}}


To build a true sized font, we create a driver file which sets the
design size of the font to be created, and then inputs Sauter's parameterised
version of the font (from the file {\tt build\_}{\it font}{\tt.mf}).
A typical invocation of |make_font| would be:

{\let\tt\smalltt\baselineskip9pt
\begintt
make_font lw canon 1000 cmb 8 9 10 11 12 14 17
\endtt
}

This command would build the font {\tt cmb} in sizes 8--17 points.
|make_font| should be run from the directory which contains the
parameterised {\tt mf} files.

The first three parameters required by |make_font| are the name of the
\MF{} |mode_def| to be used when building the font, the name of the
{\em device\/} sub-directory to place the {\tt pk} files in, and the
magnification of the font.
An optional switch can be used to set the command name under which \MF{}
is invoked.

{\let\tt\smalltt\baselineskip9pt\parindent0pt
\begintt
#|iteight beginning of script|tt
#! /bin/csh -f
# Make a font, at the specified sizes.
# make_font mode pkdir mag font size...

# MF name parameter; 
#     assume cmbase preloaded otherwise.
if ($#argv != 0 &amp;&amp; $argv[1] =~ -*) then
    set meta=`echo $argv[1] | cut -c2-`; shift
else
    set meta=cmmf
endif

if ($#argv == 0) then
    echo "No mode name"; exit 1
else
    set mode=$1; shift
endif

if ($#argv == 0) then
    echo "No pk directory"; exit 1
else
    set pkdir=./pk/$1; shift
endif
\endtt
\begintt
if ($#argv == 0) then
    echo "No magnification"; exit 1
else
    set mag="$1"; shift
endif
if ($#argv == 0) then
    echo "No font"; exit 1
else
    set font=$1; shift
endif
\endtt
}



Note that the magnification can also be given in terms of {\it  magsteps\/}.
The command to build {\tt cmr} in 10-point, magnified $1.2$ times would be:

{\let\tt\smalltt\baselineskip9pt
\begintt
make_font lw canon "magstep1*1000" cmr 10
\endtt
}

The names of the directories in which the {\tt tfm} files and \MF{} driver
files go are then set up, and directories created if necessary. The name of
the default \MF{} inputs directory (the last line of this next section) may
need changing:

%script
{\let\tt\smalltt\baselineskip9pt\parindent0pt
\begintt
#|iteight continuation of script|tt
# directories for created font files
set tfmdir=./tfm
set mfdir=./mf
set gftopk=gftopk

if (! -d $pkdir) mkdir $pkdir
if (! -d $tfmdir) mkdir $tfmdir
if (! -d $mfdir) mkdir $mfdir

# Include the standard Computer Modern files, 
# like roman.mf, romanu.mf, etc.
setenv MFINPUTS \ 
    .:${mfdir}:/usr/local/share/tex/fonts/mf
\endtt
}

The next parameter required by the script is the name of the font to
be created. This is followed by a list of sizes in which the font is to
be built. The script iterates over the sizes available, creating driver files
if there is a parameterised version of the font available. If there is not a
parameterised version of the font available, the script assumes that the font
is available anyway, and that the name of the file in which it is found is the
name of the font  and the size concatenated together. There is one special
case to worry about though; some fonts do not have size information in their
names (for example {\tt manfnt} or {\tt cminch}); these fonts can be built by
putting a single empty string instead of the list of sizes. For example:

{\let\tt\smalltt\baselineskip9pt
\begintt
make_font lw canon 1000 cminch ""
\endtt
}

This command will build the font {\tt cminch}, if the driver file
{\tt cminch.mf} exists in any of the \MF{} input directories.

%script
{\let\tt\smalltt\baselineskip9pt\parindent0pt
\begintt
#|iteight continuation of script|tt
echo "Creating $font $argv @ mag $mag"

# iterate over sizes
while ($#argv &gt; 0)
 set size=$argv[1]; shift argv
 set file=$font$size
 set mffile=$mfdir/$file.mf
\endtt
\begintt
 # build mf file if build procedure present
 # otherwise assume mf file is already built
 if (! -e $mffile &amp;&amp; -f "build_$font.mf") then
  echo "...creating $mffile"
  echo "% $size-point $font." &gt; $mffile
  echo "design_size := $size;" &gt;&gt; $mffile
  echo "input build_$font;" &gt;&gt; $mffile
 endif
\endtt
}

|make_font| then calls \MF{}, sets the mode and magnification, and
inputs the driver file.
The {\tt batchmode} command prevents \MF{} from stopping if it detects an
error; the error is written to a log file and processing continues.

{\let\tt\smalltt\baselineskip9pt\parindent0pt
\begintt
#|iteight continuation of script|tt
$meta "\batchmode;mode:=$mode;mag:=$mag/1000;input $file"
\endtt
}

The next line looks at the last line of the log file produced by \MF{} to
determine what the resolution and filename of the generated {\tt gf} font was.
If the \MF{} run was successful, the last line of the log file will contain a
line similar to:

{\let\tt\smalltt\baselineskip9pt
\begintt
Output written on manfnt.210gf 
           (122 characters, 13588 bytes).
\endtt
}

The {\tt sed} expression on this line extracts the filename and resolution from
this line, storing them in the variable {\tt log}. (Relying on \MF{} putting
this information on the last line of the log is not a good idea; the actual
version of |make_font| I use is identical to the one here, except that it
has the search pattern
|/^Output *written *on *[^.]*\.[0-9]*gf/| in place of |$|.)

{\let\tt\smalltt\baselineskip9pt\parindent0pt
\begintt
#|iteight continuation of script|tt
set log=`sed -n \
   '$s/.*on *\([^.]*\)\.\([0-9]*\)gf.*$/\1 \2/p' \
   $file.log`
\endtt
}

The script now checks whether the filename and resolution  were found
correctly. If they were, the {\tt gf} file is converted to a {\tt pk} file
and stored in an appropriate directory, the {\tt tfm} file is moved to an
appropriate directory, and any leftover files are cleaned up. If the
name and resolution were not found, the log file is printed to the standard
output, and leftover files are cleaned up.

{\let\tt\smalltt\baselineskip9pt\parindent0pt
\begintt
#|iteight continuation of script|tt
if ($#log == 2) then
 set out=$log[1];
 set dpi=$log[2]
 if (! -d $pkdir/dpi$dpi) mkdir $pkdir/dpi$dpi
 echo "$out.${dpi}gf converted to $pkdir/dpi$dpi/$file.pk"
 $gftopk $out.${dpi}gf $pkdir/dpi$dpi/$file.pk
 /bin/mv -f $out.tfm $tfmdir
 /bin/rm -f $out.${dpi}gf $file.log $out.tfm
else
 echo "Problem; $file.log ="
 cat $file.log
 /bin/rm -f $file.log $file.tfm
endif
end
\endtt
}

\section{Driving the {\ttit make\_font} script}
The |make_font| script is usually driven by another C-shell script, which
builds all of the fonts required at one mode and magnification. This script
contains commands similar to the |make_font| commands shown above, but
parameterised on the \MF{} mode name, {\tt pk} directory name, and
magnification:

%script
{\let\tt\smalltt\baselineskip9pt\parindent0pt
\begintt
# ... set up parameters $mode, $pk and $mag
#
# TeX/LaTeX "math" fonts
#
make_font $mode $pk "$mag" cmbsy 
        5 6 7 8 9 10 11 12 14 17
make_font $mode $pk "$mag" cmmi 
  5 6 7 8 9 10 11 12 14 17 20 25
make_font $mode $pk "$mag" cmmib 
        5 6 7 8 9 10 11 12 14 17
# ... etc.
make_font -logomf $mode $pk "$mag" 
        logobf 10
make_font -logomf $mode $pk "$mag" 
        logosl 10
make_font -mf $mode $pk "$mag" manfnt ""
\endtt
}

The command name switch is used to select versions of \MF{} with different
bases preloaded for the {\tt logo} and {\tt manfnt} fonts. Note that the
magnification parameter is quoted; if you use magnifications similar to
the |"magstep1*1000"| example above, this is required to prevent the
C-shell expanding the {\tt *}.

\section{Conclusion}
After you have built your true-sized font, what then? To get \LaTeX{} to work
with these fonts involves editing {\tt lfonts.tex} (or, if you are using
Mittelbach and Sch\"opf's font selection scheme, {\tt fontdef.tex}), and
replacing all of the magnified fonts with true-sized fonts. You then need to
regenerate the \LaTeX{} formats with the new fonts (by running \IniTeX). I
have found it useful to keep a copy of the original format around to allow
users to create {\tt dvi} files which can (probably) be printed at other
installations, but as this precludes deleting the old scaled fonts, it might
not be feasible for everybody.

\smallskip
\line{\box1}
\smallskip

The script presented here has made the job of building new fonts from John
Sauter's parameterised Computer Modern quicker. Table~4
shows the sizes of the font directories created for our installation. The
canon directory at
300\,\dpi\ also contains the {\tt msym} and {\tt msxm} symbol fonts among
others, so the directory size is a little inflated. 

\endgroup
\enddoublecolumns
\vfill\eject
\begindoublecolumns
I have not yet had time to find out if the set of sizes and fonts presented
here is sufficient, but I will report back to \TeXline\ about further
developments.
I have recently changed our \dvi\ to \PS\ converter to Tom Rokicki's {\tt
dvips}. This program comes with a shell script ({\tt MakeTeXPK)} which is
used to create fonts which are not available. I have now modified the {\tt
MakeTeXPK} script so that it can create true-sized fonts on demand. The {\tt
makefont} script described here is still useful for creating large batches
of fonts.
One unresolved issue which needs further investigation involves the fonts
required for photo-reduction. When the true-sized fonts are reduced from A4 to
A5 they look poor, due to fine lines disappearing. Possible solutions to this
problem include using different |mode_def|s to improve reduction quality,
or building a restricted set of fonts at a larger magnification.
\author{Angus Duggan}


\endinput
</pre></body></html>