%%%% This is the main source for the French Cursive font. %%%% (c) Emanuel Beffara, 2001--2011. This work is covered by the LPPL licence. %%%% %%%% You can get a pretty-printed document with the commented source code (and %%%% especially the first page with an explanation of the parameters) by first %%%% running "mft frcursive" to get the TeX source and then compiling the %%%% driver file "fcsource.tex" (normally shipped with this source file). This %%%% compilation needs the standard 10-pt version (driver "frcr10.mf") to be %%%% available. The document is 52 pages long. %%%% %%\title French Cursive, %% a cursive handwriting font in \MF \cr %% \fc so you can write like this. %%{\parindent=2em \parskip=1ex %% %% The main difficulty in the design of a good cursive font lies in the fact %% that words must appear to be written in a single pen stroke. So words will %% actually consist in a succession of letter glyphs and link glyphs, and the %% shapes of the links will have to be adapted to the surrounding letters. %% Here we fully exploit \MF's ligatures system by letting it insert the link %% glyphs automatically between letters. %% %% In the following definitions, the letter glyphs correspond to the %% invariable parts of a letter's shape. For instance, in the glyph of a %% letter with a high loop like {\def\fs#1{{\fc\smash#1}} \fs b, \fs f, \fs h, %% \fs k, or \fs l}, the stroke starts at the top of the loop because the %% initial part depends on the height the previous letter starts at. The link %% glyphs are located in the range 0--31, which is reserved for accents and %% common ligatures in the T1 encoding. %% %% This file won't generate a font by itself. It is supposed to be read by a %% driver file after setting several parameters to control the actual shape of %% the font. The required parameters are the following: %% \item absolute dimensions: \deflist{% %% \\{ex}\SH & the base height (height of small letters like {\fc a})\cr %% \\{thin}\SH & the thickness of line ends\cr %% \\{med}\SH & the thickness of hairlines\cr %% \\{thick}\SH & the thickness of stems\cr %% \\{dot\_size}\SH & the diameter of dots\cr} %% \item ratios: \deflist{% %% \\{base\_width} & base width of the font with respect to \\{ex}\SH{} %% (this is the width of an unlinked {\fc a})\cr %% \\{slant} & the slant ratio to be applied\cr} %% \item widths, relative to \\{base\_width}: \deflist{% %% \\{accent\_wd} & base width of accents %% (width of acute and grave accents)\cr %% \\{link\_width} & the width of inter-letter links\cr} %% \item heights, relative to \\{ex}\SH: \deflist{% %% \\{straight\_ascend} & height of ascending bars like {\fc t}\cr %% \\{loop\_ascend} & height of ascending loops like {\fc\smash l}\cr %% \\{uc\_ascend} & height of uppercase letters\cr %% \\{straight\_descend} & depth of descending bars like {\fc\smash p}\cr %% \\{loop\_descend} & depth of descending loops like {\fc\smash j}\cr %% \\{dot\_height} & height of the dot of {\fc i} and {\fc\smash j} %% above the base line\cr %% \\{accent\_bot} & height of the bottom of accents\cr %% \\{accent\_top} & height of the top of accents\cr %% \\{cedilla\_dp} & depth of the {\it top} of the cedilla's loop\cr} %%} %%%% These are MFT formatting definitions: %%% length penpos make_accented make_cedilla %%% length label penlabels range save_letter %%% and thru %%% end bye %%%% We don't want one-line comments to be right-aligned: %%\def\9{$\quad{\eightrm\%}} %%%% vim: set foldmethod=marker : %%\sec Global definitions. %{{{1 %% Once all parameters are defined, we can compute the non-sharp values of the %% absolute dimensions according to the current mode. define_pixels(ex); define_whole_blacker_pixels(med, thin, thick, dot_size); %% The \cs\fontdimen\ registers are also computed here. The ones for spacing %% are kind of arbitrary, but these values look right. font_slant slant; font_normal_space 3/2 * base_width * ex#; font_normal_shrink 1/2 * base_width * ex#; font_normal_stretch 1/2 * base_width * ex#; font_x_height ex#; font_quad 2 * base_width * ex#; %% The following three constants describe the possible types of links. Low %% links are horizontal on the base line. High links are horizontal at height %% \\{hl\_y} with respect to \\{ex}\SH: hl_y := 1/2; % the height of high links %% Medium links are lower and directed upwards. ml_y := 13/600 / link_width; % the height of medium links ml_a := angle(.288675, ml_y); % the angle of medium links %% We take care of slanted shapes by simply applying a global transformation. currenttransform := currenttransform slanted slant; %% Some shapes are defined differently in fixed-thickness mode. if unknown fixed: boolean fixed; fixed := false; fi %% Some letter shapes have to be saved: %% \item a, c, e, g, l, n, o, r, t, u, y, z and uppercase letters are normal, %% they are used for making accented variants %% \item i is dotless, it is kept for making accented versions %% \item j is dotless, its shape appears in y, G, J and Y %% \item q and s are unlinked on the right (like at the end of words), they %% are kept to make linked versions %% \item exclamation and interrogation marks are used for the spanish %% reversed version %% %% The \\{save\_letter} macro saves the picture of a given glyph so that it %% can be reused (as explained above). The first argument is a suffix that %% represents the letter, the second one is the $x$ coordinate where accents %% should be placed (i.e. roughly the middle of the letter). def save_letter (suffix ltr) (expr pos) = picture letter.ltr; letter.ltr := currentpicture; accpos.ltr := cedpos.ltr := pos; width.ltr := w; height.ltr := h; if proofing > 1: proofrule((pos,-d), (pos,h)); fi width#.ltr := charwd; % for the accented version's width height#.ltr := charht; % for the height of accented uppercase letters depth#.ltr := chardp enddef; %% Most characters have absolute widths of the same form: def ltr_wd(expr fb, fl) = (fb * base_width + fl * link_width) * ex# enddef; def ltr_w(expr fact) = ltr_wd(fact, 1) enddef; %% And some constants are useful: lnk := link_width / base_width; height_with_dot := dot_height * ex# + dot_size# / 2; ml_d := ml_a - 90; % the stroke angle for medium links pair ml_dir; ml_dir := dir ml_a; % and the line's direction %% And these multiplicative factors are simply everywhere: def u = scaled ex xscaled base_width enddef; def uu = xscaled (base_width * ex) yscaled (uc_ascend * ex) enddef; def ua = xscaled (base_width * accent_wd * ex) yscaled ((accent_top - accent_bot) * ex) shifted (0, accent_bot * ex) enddef; v := base_width * ex; %% For proof-mode, we define the following macro to mark all useful %% information. def label(expr n) = if proofing > 1: penlabels(range 1 thru n); if h > ex: proofrule((0, ex), (w, ex)); fi fi enddef; %% Hinting... def goodx expr e = begingroup save x, y; (x,y) = e; (good.x x, y) endgroup enddef; def goodxy expr e = begingroup save x, y; (x,y) = e; (good.x x, good.y y) endgroup enddef; pickup pencircle scaled thick; thickpen := savepen; pickup pencircle scaled med; medpen := savepen; pickup pencircle scaled thin; thinpen := savepen; %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %%\sec Lowercase letters. %{{{1 a_left := 1/3; % the height of the left end of small loops "The letter a"; beginchar("a", ltr_w(7/6), ex#, 0); penpos1(med, 0); x1r = hround (base_width * ex); y1 = 2/3 ex; penpos2(med, 90); z2r = (3/5, 1) u; penpos3(thick, 180); z3r = (0, a_left) u; penpos4(med, 270); z4r = (1/2, 0) u; penpos5(med, 0); x5 = x1; y5 = 1/3 ex; penstroke z1e .. z2e .. tension 1.2 .. z3e .. z4e{right} .. z5e ; penpos6(thick, 195); z6 = z1 + (1/10, 2/9) u; penpos7(thick, 180); z7r = z1l; penpos8(thick, 180); z8r = z5l; penpos9(med, 270); z9r = (7/6 + lnk, 0) u; penstroke z6e .. z7e .. tension 2 .. z8e .. {right}z9e ; label(9); save_letter(a)(x2); cedpos.a := x9; endchar; "The letter b"; beginchar("b", ltr_w(1), loop_ascend * ex#, 0); penpos2(med, 330); z2 = goodx (3/4, 2/3 * loop_ascend) u ; penpos3(med, 100); z3r = (4/10, loop_ascend) u ; penpos4(thick, 180); z4r = goodx (0, 3/5 * loop_ascend) u ; penpos5(thick, 180); x5 = x4; y5 = ex ; penpos6(med, 260); z6r = (1/2, 0) u ; penpos7(med, 0); z7 = (v, y10l); penpos8(thin, 135); z8 = z7l + (-1, 1) * ex / 6 ; penpos9(med, 270); z9l = z7l ; penpos10(med, 270); z10 = (1 + lnk, hl_y) u; penstroke z2e{up} .. tension 1.2 .. z3e .. controls (x4e,y3e) and (x4e,2/3[y3e,y4e]) .. z4e .. z5e{down} .. z6e .. {up}z7e .. z8e .. {right}z9e .. {right}z10e ; label(10); endchar ; "The letter c"; beginchar("c", ltr_w(1), ex#, 0); penpos1(med, 30); z1r = (1, 3/4) u; penpos2(med, 90); z2r = (3/5, 1) u; penpos3(thick, 180); z3r = (0, a_left) u; penpos4(med, 270); z4r = (1/2, 0) u; penpos5(med, ml_d); z5 = (1 + lnk, ml_y) u; penstroke z1e .. z2e .. tension 1.2 .. z3e .. z4e{right} .. {ml_dir}z5e ; label(5); save_letter(c)(3/5 v); endchar ; "The letter d"; beginchar("d", ltr_w(7/6), straight_ascend * ex#, 0); penpos1(med, 0); x1r = hround (base_width * ex); y1 = 2/3 ex; penpos2(med, 90); z2r = (3/5, 1) u; penpos3(thick, 180); z3r = (0, a_left) u; penpos4(med, 270); z4r = (1/2, 0) u; penpos5(med, 0); z5r = (1, 1/3) u; penstroke z1e .. z2e .. tension 1.2 .. z3e .. z4e{right} .. z5e ; penpos6(thick, 170); x6r = x1l; y6 = straight_ascend * ex; penpos7(thick, 180); x7r = x1l; y7 = 2/3 * straight_ascend * ex; penpos8(thick, 180); x8r = x7r; y8 = y5; penpos9(med, 270); z9r = (7/6 + lnk, 0) u; penstroke z6e .. {down}z7e .. {down}z8e .. {right}z9e ; label(9); save_letter(d)(x6); endchar; "The letter e"; beginchar("e", ltr_w(1), ex#, 0); penpos1(med, 270); z1 = (thin, 1/2 * ex) ; penpos2(med, 270); z2 = (1/2, 1/2) u; penpos3(med, 0); z3r = (1, 3/4) u; penpos4(med, 90); z4r = (3/5, 1) u; penpos5(thick, 180); z5r = (0, a_left) u; penpos6(med, 270); z6r = (1/2, 0) u; penpos7(med, ml_d); z7 = (1 + lnk, ml_y) u; penstroke z1e .. z2e{right} .. tension 1.2 .. {up}z3e .. z4e .. tension 1.2 .. z5e .. z6e{right} .. {ml_dir}z7e ; label(7); save_letter(e)(3/5 v); endchar ; "The letter f"; beginchar("f", ltr_w(5/6), loop_ascend * ex#, loop_descend * ex#); penpos2(med, 330); z2 = goodx (3/4, 2/3 * loop_ascend) u ; penpos3(med, 100); z3r = (4/10, loop_ascend) u ; penpos4(thick, 180); z4r = (0, 3/5 * loop_ascend) u ; penpos5(thick, 180); z5r = (0, -1/3 * loop_descend) u ; penpos6(med, 270); z6r = (4/10, - loop_descend) u ; penpos7(med, 0); z7r = goodx (8/9, -2/5 * loop_descend) u ; penpos8(med, 25); z8 = (2/3, 1/6) u ; penpos9(thin, 135); z9 = z8 + (-2, 1) * ex / 9 ; penpos10(med, 270); z10r = (2/3, 0) u ; penpos11(med, ml_d); z11 = (5/6 + lnk, ml_y) u; penstroke z2e{up} .. tension 1.2 .. z3e .. controls (x4e,y3e) and (x4e,2/3[y3e,y4e]) .. z4e .. z5e .. controls (x5e,2/3[y6e,y5e]) and (x5e,y6e) .. z6e .. tension 1.2 .. z7e {up} .. z8e {z9-z7} .. tension 1.1 .. {dir 225} z9e .. tension 1.1 .. {right}z10e .. {ml_dir}z11e ; label(11); endchar ; "The letter g"; beginchar("g", ltr_w(9/8), ex#, loop_descend * ex#); penpos1(med, 0); x1r = hround (base_width * ex); y1 = 2/3 ex; penpos2(med, 90); z2r = (3/5, 1) u; penpos3(thick, 180); z3r = (0, a_left) u; penpos4(med, 270); z4r = goodx (1/2, 0) u; penpos5(med, 0); x5r = x1r; y5 = 1/3 ex; penstroke z1e .. z2e .. tension 1.2 .. z3e .. z4e .. z5e ; penpos6(thick, 190); z6 = z1 + (1/10, 2/9) u; penpos7(thick, 180); z7r = z1l; penpos8(thick, 180); x8r = x5l; y8 = -1/3 * loop_descend * ex; penpos9(med, 90); x9 = x4; y9l = vround (-loop_descend * ex); penpos10(med, 315); z10l = (1/4, -1/3 * loop_descend) u; penpos11(med, ml_d); z11 = (9/8 + lnk, ml_y) u; penstroke z6e .. z7e{down} .. {down}z8e .. tension 1.1 .. z9e .. z10e .. {ml_dir}z11e ; label(11); save_letter(g)(x2); endchar; "The letter h"; beginchar("h", ltr_w(1), loop_ascend * ex#, 0); penpos2(med, 330); z2 = goodx (3/4, 2/3 * loop_ascend) u ; penpos3(med, 100); z3r = (4/10, loop_ascend) u ; penpos4(thick, 180); z4r = goodx (0, 3/5 * loop_ascend) u ; penpos5(thick, 180); z5r = (0, 0) u ; penstroke z2e{up} .. tension 1.2 .. z3e .. controls (x4e,y3e) and (x4e,2/3[y3e,y4e]) .. z4e .. z5e ; penpos6(thick, 0); z6l = (0, 1/3) u; penpos7(med, 270); z7l = (0.55, 1) u; penpos8(thick, 180); x8l = hround (base_width * ex); y8 = 1/2 ex; penpos9(med, 270); z9r = (1 + lnk, 0) u; penstroke z6e{up} .. tension 1.4 .. z7e %.. tension 1.1 .. {down}z8e .. {right}z9e; label(9); endchar; "The letter i"; beginchar("i", ltr_w(1/2), height_with_dot, 0); penpos1(thick, 180); x1r = hround (base_width * ex / 6); y1 = ex; penpos2(thick, 180); x2r = x1r; y2r = 2/3 ex; penpos3(med, 270); z3r = (1/2 + lnk, 0) u; penstroke z1e -- z2e{down} .. {right}z3e; save_letter(i)(x1); height.i := ex; height#.i := ex#; % the letter is saved without the dot pickup pencircle scaled thick; x4 = x1; y4 = dot_height * ex; pickup pencircle scaled dot_size; drawdot z4; label(4); endchar; "The letter j"; beginchar("j", ltr_w(7/8), ex#, loop_descend * ex#); penpos1(thick, 180); z1 = good.lft ((3/4, 1) u); penpos2(thick, 180); x2 = x1; y2 = -1/3 loop_descend * ex; penpos3(med, 90); x3 = x1/3; y3l = vround (-loop_descend * ex); penpos4(med, 315); z4 = (0, -1/3 * loop_descend) u; penpos5(med, ml_d); z5 = (7/8 + lnk, ml_y) u; penstroke z1e{down} .. {down}z2e .. tension 1.1 .. z3e .. z4e .. {ml_dir}z5e; save_letter(j)(x1); pickup pencircle scaled thick; x6 = x1; y6 = dot_height * ex; pickup pencircle scaled dot_size; drawdot z6; label(6); endchar; "The letter k"; beginchar("k", ltr_w(5/6), loop_ascend * ex#, 0); penpos2(med, 330); z2 = goodx (3/4, 2/3 * loop_ascend) u ; penpos3(med, 100); z3r = (4/10, loop_ascend) u ; penpos4(thick, 180); z4r = (0, 3/5 * loop_ascend) u ; penpos5(thick, 180); z5r = (0, 0) u ; penstroke z2e{up} .. tension 1.2 .. z3e .. controls (x4e,y3e) and (x4e,2/3[y3e,y4e]) .. z4e .. z5e ; penpos6(med, 270); z6 = (thick, 13/16 * ex); penpos7(med, 180); z7l = goodx (8/9, 9/16) u; penpos8(med, 90); z8 = (1/8, 2/5) u; penstroke z6e{dir 60} .. {down}z7e .. tension 1.3 .. {dir 140}z8e; penpos9 (med, 270); z9 = z8; penpos10(med, 270); z10r = (5/6 + lnk, 0) u; penstroke z9e{dir 10} .. tension 0.8 ..{right}z10e; label(11); endchar; "The letter l"; beginchar("l", ltr_w(2/3), loop_ascend * ex#, 0); penpos2(med, 330); z2 = goodx (3/4, 2/3 * loop_ascend) u; penpos3(med, 100); z3r = (4/10, loop_ascend) u; penpos4(thick, 180); z4r = (0, 3/5 * loop_ascend) u; penpos5(thick, 180); z5r = (0, 1) u; penpos6(med, 260); z6r = (1/2, 0) u; penpos7(med, ml_d); z7 = (2/3 + lnk, ml_y) u; penstroke z2e{up} .. tension 1.2 .. z3e .. controls (x4e,y3e) and (x4e,2/3[y3e,y4e]) .. z4e -- z5e .. controls (x5e,1/2[y5e,y6e]) and (x5e,y6e) .. z6e .. {ml_dir}z7e ; label(7); save_letter(l)(x3); endchar ; "The letter m"; beginchar("m", ltr_w(13/6), ex#, 0); pickup thickpen; penpos1(med, 270); z1l = (1/3, 1) u; penpos2(thick, 180); z2 = good.lft ((2/3, 1/3) u); penpos3(thick, 180); x3 = x2; y3 = 0; penstroke z1e{right} .. {down}z2e -- z3e; penpos4(thick, 0); z4 = z2; penpos5(med, 270); z5l = (1, 1) u; penpos6(thick, 180); z6 = good.lft ((4/3, 1/3) u); penpos7(thick, 180); x7 = x6; y7 = 0; penstroke z4e{up} .. {right}z5e .. {down}z6e -- z7e; penpos8 (thick, 0); z8 = z6; penpos9 (med, 270); z9l = (5/3, 1) u; penpos10(thick, 180); x10 - x6 = x6 - x2; y10 = 2/5 ex; penpos11(med, 270); z11r = (13/6 + lnk, 0) u; penstroke z8e{up} .. {right}z9e .. {down}z10e .. {right}z11e; label(11); endchar; "The letter n"; beginchar("n", ltr_w(3/2), ex#, 0); pickup thickpen; penpos1(med, 270); z1l = (1/3, 1) u; penpos2(thick, 180); z2 = good.lft ((2/3, 1/3) u); penpos3(thick, 180); z3 = (2/3, 0) u; penstroke z1e{right} .. {down}z2e -- z3e; penpos4(thick, 0); z4 = z2; penpos5(med, 270); z5l = (1, 1) u; penpos6(thick, 180); z6 = good.lft ((4/3, 2/5) u); penpos7(med, 270); z7r = (3/2 + lnk, 0) u; penstroke z4e{up} .. {right}z5e .. {down}z6e .. {right} z7e; label(7); save_letter(n)(x2); endchar; "The letter o"; beginchar("o", ltr_w(9/8), ex#, 0); penpos1(med, 330); z1r = (1, 7/10) u; penpos2(med, 90); z2r = (1/2, 1) u; penpos3(thick, 180); z3r = (0, a_left) u; penpos4(med, 270); z4r = (3/5, 0) u; penpos5(med, 0); z5r = (9/8, 1/2) u; penpos6(med, 60); z6 = (7/8, 8/10) u; penpos7(med, 220); z7 = (5/8, 3/5) u; penpos8(med, 270); z8 = (9/8 + lnk, hl_y) u; penstroke z1e .. z2e .. tension 1.1 .. z3e .. z4e .. {up}z5e .. {dir 150}z6e .. {dir 310}z7e .. {right}z8e; label(8); save_letter(o)(1/2[x3r,x5r]); endchar ; "The letter p"; beginchar("p", ltr_w(7/4), ex#, straight_descend * ex#); pickup thickpen; penpos1(thick, 180); z1 = good.lft ((3/4, 1) u); penpos2(thick, 180); x2 = x1; y2 = vround (-straight_descend * ex); penstroke z1e -- z2e; penpos3(med, 0); z3r = (x1l, 0); penpos4(med, 270); z4l = (5/4, 1) u; penpos5(thick, 180); penpos6(med, 270); z6r = (7/4 + lnk, 0) u; z5 = good.lft ((1/2[x4,x6], 1/2 * ex)); penstroke z3e{up} .. tension 1.2 .. {right}z4e .. z5e .. {right}z6e; label(6); endchar; "The letter q with no link"; beginchar("q", ltr_wd(1, 0) + thick# - med#, ex#, straight_descend * ex#); penpos1(med, 0); x1r = hround (base_width * ex); y1 = 2/3 ex; penpos2(med, 90); z2r = (3/5, 1) u; penpos3(thick, 180); z3r = (0, a_left) u; penpos4(med, 270); z4r = (1/2, 0) u; penpos5(med, 0); x5 = x1; y5 = 1/3 ex; penstroke z1e .. z2e .. tension 1.2 .. z3e .. z4e{right} .. z5e ; penpos6(thick, 195); z6 = z1 + (1/10, 2/9) u; penpos7(thick, 180); z7r = z1l; penpos8(thick, 180); x8r = x5l; y8 = vround (-straight_descend * ex); penstroke z6e .. z7e --- z8e; picture letter.q; letter.q := currentpicture; % We keep the glyph for the linked version. label(8); endchar; "The letter r"; beginchar("r", ltr_w(5/4), 6/5 ex#, 0); penpos1(med, 0); z1l = (1/6, 1) u; penpos2(med, 90); z2r = z1l + (-1/3,1)/5 u; penpos3(med, 270); z3l = z1l; penpos4(med, 220); %z4l = (1, 1) u; %z4l = (x5l,y3l); z4r = (x5r,y3r); penpos5(thick, 180); z5l = (9/8, 2/5) u; penpos6(med, 270); z6r = (5/4 + lnk, 0) u; penstroke z1e{up} .. z2e .. z3e .. tension 1.4 .. z4e .. tension 1.3 .. {down}z5e .. {right}z6e; label(6); save_letter(r)(1/2[x1,x4]); height.r := ex; height#.r := ex#; endchar; "The letter s with no link"; beginchar("s", ltr_wd(5/4, 0), 7/6 ex#, 0); penpos0(thick, 0); z0 = good.rt ((3/4, 1) u); penpos1(med, 0); z1l = z0l; penpos2(med, 90); z2r = z1l + (0, 1/6) u; penpos3(med, 210); z3l = z1l; penpos4(thick, 180); z4l = (5/4, 1/3) u; penpos5(med, 90); z5l = (5/8, 0) u; penpos6(med, 300); z6 = (1/2, 2/5) u; penstroke z1e{dir 60} .. z2e .. z3e{dir 315} .. tension 1.2 .. z4e .. {left}z5e .. {dir 30}z6e; picture letter.s; letter.s := currentpicture; % Same trick as for the q. label(6); save_letter(s)(x5); height.s := ex; height#.s := ex#; endchar; "The letter t"; beginchar("t", ltr_w(7/8), straight_ascend * ex#, 0); penpos1(thick, 180); z1r = goodx (1/6, straight_ascend) u; penpos2(thick, 180); z2r = goodx (1/6, 2/3) u; penpos3(med, 270); z3r = (2/3, 0) u; penpos4(med, ml_d); z4 = (7/8 + lnk, ml_y) u; penstroke z1e -- z2e{down} .. {right}z3e .. {ml_dir}z4e; penpos5(med, 270); z5l = goodxy (1/6 * v + med, 2/3 * straight_ascend * ex); penpos6(med, 270); z6l = goodxy (1, 2/3 * straight_ascend) u; penstroke z5e -- z6e; label(6); save_letter(t)(x3); endchar; "The letter u"; beginchar("u", ltr_w(4/3), ex#, 0); penpos1(thick, 180); z1r = goodx (1/6, 1) u; penpos2(thick, 180); x2 = x1 ; y2 = 1/2 ex; penpos3(med, 270); x3 = 1/2[x2,x4]; y3r = 0; pickup thickpen; penpos4(thick, 0); z4 = good.lft ((7/6, 1/2) u); penpos5(thick, 0); x5 = x4 ; y5 = ex ; penstroke z1e -- z2e{down} .. {right}z3e .. {up}z4e -- z5e; penpos6(thick, 180); z6 = z4; penpos7(med, 270); z7r = (4/3 + lnk, 0) u; penstroke z6e{down}.. {right}z7e; label(7); begingroup save u; save_letter(u)(1/2[x1,x5]); endgroup endchar; "The letter v"; beginchar("v", ltr_w(10/6), ex#, 0); pickup thickpen; penpos1(med, 270); z1l = (1/3, 1) u; penpos2(thick, 180); z2 = good.lft ((1/2, 1/2) u); penpos3(med, 270); z3r = (1, 0) u; penpos4(med, 0); z4 = goodx (3/2, 5/8) u; penpos5(med, 150); z5r = (7/6, 15/16) u; penpos6(med, 270); z6 = (10/6 + lnk, hl_y) u; penstroke z1e{right} .. tension 1.2 .. {down} z2e .. {right}z3e .. {up}z4e .. tension 0.8 .. {dir 240}z5e .. {right}z6e; label(6); endchar; "The letter w"; beginchar("w", ltr_w(13/6), ex#, 0); pickup thickpen; penpos1(med, 270); z1l = (1/3, 1) u; penpos2(thick, 180); z2 = good.lft ((1/2, 1/2) u); penpos3(med, 270); z3r = (7/8, 0) u; penpos5(thick, 180); z5 = good.lft ((9/8, 7/8) u); penpos4(med, 0); z4l = z5r; penstroke z1e{right} .. tension 1.2 .. {down}z2e .. {right}z3e .. tension 1.3 .. {up}z4e; penpos6(med, 270); z6r = (13/8, 0) u; penpos7(med, 0); z7 = goodx (2, 5/8) u; penpos8(med, 150); z8r = (5/3, 15/16) u; penpos9(med, 270); z9 = (13/6 + lnk, hl_y) u; penstroke z5e{down} .. tension 1.3 .. {right}z6e .. {up}z7e .. tension 0.8 .. {dir 240}z8e .. {right}z9e; label(9); endchar; "The letter x"; beginchar("x", ltr_w(8/5), ex#, 0); penpos0(med, 300); z0 = (-1/5, 5/6) u; penpos1(med, 270); z1l = (1/3, 1) u; penpos2(thick, 180); z2 = (4/5, 1/2) u; penpos3(med, 90); z3l = (1/3, 0) u; penpos4(med, 45); z4 = (0, 1/8) u; penstroke z1e{right} .. {dir 270}z2e .. {left}z3e .. {dir 135}z4e; penpos5(med, 45); z2 = 1/2 [z4, z5]; penpos6(med, 270); z2 = 1/2 [z1, z6]; penpos7(med, ml_d); z7 = (8/5 + lnk, ml_y) u; penstroke z5e{dir 135} .. {dir 270}z2e .. {right}z6e .. {ml_dir}z7e; label(7); endchar; "The letter y"; beginchar("y", width#.j + (3v/2 - accpos.j + lnk) / ex * ex#, ex#, loop_descend * ex#); pickup thickpen; penpos1(med, 270); z1l = (1/3, 1) u; penpos2(thick, 180); z2 = good.lft ((1/2, 1/2) u); penpos3(med, 270); z3r = (1/2[x2,x4], 0); penpos4(med, 0); z4l = z5r; penpos5(thick, 180); z5 = (3/2, 1) u; penstroke z1e{right} .. {down}z2e .. {right}z3e .. {up}z4e; addto currentpicture also letter.j shifted (x5 - accpos.j, 0); label(4); save_letter(y)(x3); endchar; "The letter z"; beginchar("z", ltr_w(11/6), 6/5 * ex#, loop_descend * ex#); penpos1(med, 0); z1l = (1/6, 1) u; penpos2(med, 90); z2r = z1l + (-1/3,1)/5 u; penpos3(med, 270); z3l = z1l; penpos4(thick, 210); z4l = (9/8, 1) u; penpos5(med, 135); z5 = (2/3, 0) u; penstroke z1e{up} .. z2e .. z3e .. z4e .. {dir 225}z5e; penpos6(med, 315); z6 = z5; penpos7(thick, 220); z7 = (5/4, 1/5) u; penpos8(thick, 155); z8 = (7/4, -4/9 * loop_descend) u; penpos9(med, 90); z9l = (1, -loop_descend) u; penpos10(med, 315); z10 = (7/8, -1/3 * loop_descend) u; penpos11(med, ml_d); z11 = (11/6 + lnk, ml_y) u; penstroke z6e{dir 45} .. z7e .. z8e .. tension 1.3 .. z9e .. z10e .. tension 1.4 .. {ml_dir}z11e; label(8); save_letter(z)(1/2[x1,x4]); height.z := ex; height#.z := ex#; endchar; "The ligature oe"; beginchar(247, ltr_w(2), ex#, 0) addto currentpicture also letter.o; addto currentpicture also letter.e shifted ((1,0) u); endchar; %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %%\sec Uppercase letters. %{{{1 hgt := uc_ascend * ex#; %% The small loop at the beginning of H, I, J and K is the same. picture small_loop; "The letter A"; beginchar("A", ltr_wd(3,0), hgt, 0); %% The left bar: penpos1(thin, 0); z1 = (3/5, 2/9) uu; penpos2(med, 90); z2l = (2/5, 1/3) uu; penpos3(med, 180); z3r = (0, 1/6) uu; penpos4(med, 280); z4r = (2/5, 0) uu; penpos5(med, 0); z5 = (7/6, 1/2) uu; penpos6(med, 320); z6 = (3/2, 1) uu; penstroke z1e .. {left}z2e .. z3e .. z4e .. {up}z5e .. z6e; %% The right bar: penpos7(med, 145); z7 = z6; penpos8(thick, 180); z8l = (3/2, 5/12) uu; penpos9(med, 270); z9r = (6/3, 0) uu; penpos10(med, 0); z10r = (3, 1/3) uu; penpos11(med, 90); z11 = (5/2, 2/3) uu; penpos12(thin, 240); z12 = (17/8, 1/3) uu; penstroke z7e .. z8e{down} .. z9e .. z10e .. tension 1.2 .. {left}z11e .. {dir 290}z12e; %% The horizontal bar: penpos13(thin, 330); z13 = (7/8, 6/12) uu; penpos14(med, 270); z14 = (13/8, 1/2) uu; penpos15(thin, 0); z15 = (11/6, 4/6) uu; penstroke z13e{dir 105} .. {right}z14e .. {dir 110}z15e; label(15); save_letter(A)(x6l); cedpos.A := x9; endchar; "The letter B"; beginchar("B", ltr_wd(5/2,0), hgt, 0); %% The vertical bar: penpos1(med, 135); z1 = (1, 1) uu; penpos2(thick, 180); z2 = (1, 2/5) uu; penpos3(med, 90); z3l = (3/5, 0) uu; penpos4(med, 330); z4l = (1/5, 1/6) uu; penstroke z1e{dir 255} .. z2e .. {left}z3e .. z4e; %% The two loops: penpos5(thin, 180); z5 = (3/5, 3/5) uu; penpos6(med, 90); z6 = (3/10, 1/3) uu; penpos7(med, 0); z7l = (0, 3/5) uu; penpos8(med, 270); z8l = (1, 1) uu; penpos9(thick, 180); z9 = (2, 7/9) uu; penpos10(med, 345); z10 = (9/8, 3/5) uu; penpos11(thick, 180); z11l = (5/2, 2/9) uu; penpos12(med, 90); z12l = (7/4, 0) uu; penpos13(med, 0); z13 = (5/4, 1/6) uu; penpos14(thin, 340); z14 = (3/2, 3/10) uu; penstroke z5e{down} .. tension 1.2 .. z6e .. tension 1.3 .. {up}z7e .. {right}z8e .. {down}z9e .. tension 1.4 .. {up}z10e .. tension 1.5 .. {down}z11e .. {left}z12e .. tension 1.0 .. z13e .. z14e; label(14); endchar; "The letter C"; beginchar("C", ltr_wd(2,0), hgt, 0); penpos1(thin, 180); z1 = (2/5, 1) uu; penpos2(med, 180); z2r = (0, 2/3) uu; penpos3(med, 270); z3 = (1, 1/2) uu; penpos4(med, 0); z4r = (2, 5/6) uu; penpos5(med, 90); z5r = (8/5, 1) uu; penpos6(thick, 180); z6r = (2/5, 2/5) uu; penpos7(med, 270); z7r = (4/3, 0) uu; penpos8(med, 0); z8 = (9/5, 1/4) u; penpos9(thin, 130); z9 = (7/5, 1/3) uu; penstroke z1e .. {down}z2e .. z3e .. z4e .. z5e .. {down}z6e .. z7e .. z8e .. z9e; label(9); save_letter(C)(x7); endchar; "The letter D"; beginchar("D", ltr_wd(13/6,0), hgt, 0); penpos1(thin, 180); z1 = (4/3, 1) uu; penpos2(thick, 180); z2 = (1, 1/2) uu; penpos3(med, 90); z3l = (1/3, 0) uu; penpos4(med, 0); z4l = (0, 1/6) uu; penpos5(med, 270); z5 = (4/5, 1/6) uu; penpos6(med, 270); z6r = (3/2, 0) uu; penpos7(thick, 0); z7r = (13/6, 1/3) uu; penpos8(med, 90); z8r = (6/7, 1) uu; penpos9(med, 180); z9r = (0, 3/4) uu; penpos10(thin, 240); z10 = (2/5, 1/2) uu; penpos11(thin, 0); z11 = (2/3, 2/3) uu; penstroke z1e .. z2e .. z3e .. z4e{up} .. z5e .. z6e .. z7e .. z8e .. z9e .. z10e .. {up}z11e; label(11); save_letter(D)(1/2[x1,x2]); endchar; "The letter E"; beginchar("E", ltr_wd(2,0), hgt, 0); penpos1(thin, 180); z1 = (1/3, 1) uu; penpos2(med, 270); z2 = (1/5, 3/4) uu; penpos3(med, 0); z3 = (8/5, 7/8) uu; penpos4(med, 90); z4r = (4/3, 1) uu; penpos5(thick, 180); z5 = (2/3, 7/10) uu; penpos6(thin, 270); z6l = (4/3, 12/20) uu; penstroke z1e .. z2e .. tension 1.3 .. z3e .. z4e .. z5e .. {right}z6e; penpos7(med, 90); z7r = z6l; penpos8(thick, 180); z8r = (1/6, 1/6) uu; penpos9(med, 270); z9r = (1, 0) uu; penpos10(med, 0); z10r = (2, 1/4) uu; penpos11(thin, 130); z11 = (7/6, 1/4) uu; penstroke z7e{left} .. z8e .. z9e .. z10e{up} .. z11e; label(11); save_letter(E)(1/2[x3,x5]); endchar; "The letter F"; beginchar("F", ltr_wd(9/4,0), hgt, 0); %% The vertical bar: penpos1(thin, 135); z1 = (6/4, 1) uu; penpos2(thick, 180); z2 = (5/4, 1/2) uu; penpos3(med, 90); z3l = (2/3, 0) uu; penpos4(thin, 330); z4 = (1/3, 1/6) uu; penstroke z1e .. {down}z2e .. z3e .. z4e; %% The upper horizontal bar: penpos5(thin, 180); z5 = (3/4, 2/3) uu; penpos6(med, 90); z6 = (1/2, 1/3) uu; penpos7(med, 0); z7l = (0, 1/2) uu; penpos8(med, 270); z8l = (4/5, 1) uu; penpos9(med, 270); z9 = (2, 5/6) uu; penpos10(thin, 90); z10r = (2, 1) uu; penstroke z5e .. tension 1.2 .. z6e .. z7e .. tension 1.2 .. z8e{right} .. {right}z9e .. z10e; %% The middle bar: penpos11(med, 270); z11 = z2r - (1/10, 0) uu; penpos12(med, 270); z12 = z2r + (2/3, 0) uu; penpos13(med, 110); z13 = z2r + (2/3, 1/12) uu; penpos14(thin, 180); z14 = z2r + (1/2, -1/6) uu; penstroke z11e .. z12e{right} .. z13e .. {down}z14e; label(14); endchar; "The letter G"; beginchar("G", ltr_w(2), hgt, loop_descend * ex#); penpos1(thin, 180); z1 = (1/2, 1) uu; penpos2(med, 200); z2r = (0, 2/3) uu; penpos3(med, 0); z3r = (2, 5/6) uu; penpos4(med, 90); z4r = (5/3, 1) uu; penpos5(thick, 180); z5r = (1/3, 1/3) uu; penpos6(med, 270); z6r = (1, 0) uu; penpos7(thick, 0); z7 = good.rt ((15/8, 1) u); penstroke z1e .. {down}z2e .. tension 1.2 .. z3e .. z4e .. tension 1.2 .. z5e .. z6e .. {up}z7e; penpos0(thick, 180); z0 = good.lft ((3/4, 1) u); addto currentpicture also letter.j shifted (z7 - z0); label(7); save_letter(G)(1/4[x4,x5]); endchar; "The letter H"; beginchar("H", ltr_wd(5/2,0), hgt, 0); %% The loop before the vertical bar: penpos1(thin, 270); z1l = (0, 7/12) uu; penpos2(med, 20); z2 = (1/6, 1) uu; penpos3(med, 250); z3l = (1/10, 29/30) uu; penpos4(thick, 0); z4 = (1, 1) uu; penstroke z1e .. {dir 110}z2e .. {dir 340}z3e .. z4e; small_loop := currentpicture; %% The letter's shape: penpos5(thick, 180); z5 = z4; penpos6(thick, 180); z6 = (1, 1/3) uu; penpos7(med, 90); z7l = (1/2, 0) uu; penpos8(med, 0); z8l = (0, 1/6) uu; penpos9(med, 315); z9 = (5/4, 1/2) uu; penpos10(med, 0); z9 = 1/2[z8, z10]; penpos11(med, 90); z9 = 1/2[z7, z11]; penpos12(thick, 180); z9 = 1/2[z6, z12]; penpos13(thick, 180); z13 = (3/2, 1/3) uu; penpos14(med, 270); z14r = (2, 0) uu; penpos15(thin, 90); z15 = (2, 1/3) uu; penstroke z5e .. z6e .. z7e .. z8e .. z9e .. z10e .. z11e .. z12e .. z13e .. z14e .. {dir 190}z15e; %% The small vertical bar in the middle: penpos16(thin, 180); z16 = z9 + (0, 1/8) uu; penpos17(thin, 180); z9 = 1/2[z16, z17]; penstroke z16e .. z17e; label(18); endchar; "The letter I"; beginchar("I", ltr_wd(1,0) + thick#/2, hgt, 0); addto currentpicture also small_loop; penpos1(thick, 180); z1 = (1, 1) uu; penpos2(thick, 180); z2 = (1, 1/3) uu; penpos3(med, 90); z3l = (3/5, 0) uu; penpos4(med, 0); z4l = (0, 1/6) uu; penpos5(thin, 270); z5 = (1/3, 1/3) uu; penstroke z1e .. {down}z2e .. z3e .. z4e .. {right}z5e; label(5); save_letter(I)(x3); endchar; "The letter J"; beginchar("J", ltr_w(9/8), hgt, loop_descend * ex#); addto currentpicture also small_loop; z0 = good.lft ((3/4, 1) uu); penpos1(thick, 180); z1 = (1, 1) uu; penpos2(thick, 180); z2 = (1, 0) uu; penstroke z1e .. z2e; addto currentpicture also letter.j shifted (z1 - z0); label(2); endchar; "The letter K"; beginchar("K", ltr_wd(7/3,0), hgt, 0); %% We get back the I's vertical bar: addto currentpicture also letter.I; %% And we add the oblique bars: penpos1(thin, 0); z1r = (7/3, 9/10) uu; penpos2(med, 90); z2r = (2, 1) uu; penpos3(thick, 180); z3 = 1/2[z2, z4]; penpos4(med, 90); z4 = (7/6, 5/12) uu; penpos5(med, 0); z5 = (5/6, 11/24) uu; penpos6(med, 270); z6 = (7/6, 1/2) uu; penpos7(thick, 180); z7 = 1/2[z6, z8]; penpos8(med, 290); z8r = (2, 0) uu; penpos9(med, 0); z9r = (7/3, 1/6) uu; penpos10(thin, 90); z10 = (2, 1/3) uu; penstroke z1e .. z2e .. z3e .. z4e .. z5e .. z6e .. z7e .. z8e .. z9e .. z10e; label(10); endchar; "The letter L"; beginchar("L", ltr_wd(7/3,0), hgt, 0); penpos1(thin, 180); z1r = (0, 1) uu; penpos2(med, 270); z2 = (7/6, 1/2) uu; penpos3(med, 0); z3r = (7/3, 5/6) uu; penpos4(med, 110); z4r = (2, 1) uu; penpos5(thick, 150); z5 = (7/6, 1/2) uu; penpos6(med, 110); z6l = (1/2, 0) uu; penpos7(med, 0); z7l = (0, 1/6) uu; penpos8(med, 240); z8 = (2/3, 1/4) uu; penpos9(med, 270); z9r = (5/3, 0) uu; penpos10(med, 0); z10r = (7/3, 1/6) uu; penpos11(thin, 180); z11 = (7/4, 1/4) uu; penstroke z1e{down} .. z2e .. z3e .. z4e .. z5e .. z6e .. z7e .. {dir -50}z8e .. {right}z9e .. z10e .. {down}z11e; label(11); save_letter(L)(x9); endchar; "The letter M"; beginchar("M", ltr_wd(10/3,0), hgt, 0); %% The left bar: penpos1(thin, 0); z1 = (1/2, 1/4) uu; penpos2(med, 180); z2r = (0, 1/5) uu; penpos3(med, 300); z3r = (1/2, 0) uu; penpos4(med, 0); z4l = (1, 1) uu; penstroke z1e{up} .. {down}z2e .. z3e .. tension 1.6 .. {up}z4e; %% The first middle bar: penpos5(thick, 180); z5r = z4l; penpos6(thick, 180); z6 = (4/3, 0) uu; penstroke z5e .. z6e; %% The second middle bar: penpos7(med, 0); z7r = z6l; penpos8(med, 0); z8l = (2, 1) uu; penstroke z7e .. {dir 70}z8e; %% The right bar: penpos9(thick, 180); z9r = z8l; penpos10(med, 270); z10r = (5/2, 0) uu; penpos11(med, 0); z11r = (10/3, 1/3) uu; penpos12(med, 90); z12 = (8/3, 2/3) uu; penpos13(thin, 180); z13 = (7/3, 1/3) uu; penstroke z9e{dir 250} .. tension 1.5 .. {right}z10e .. z11e .. z12e .. {down}z13e; label(13); endchar; "The letter N"; beginchar("N", ltr_wd(3,0), hgt, 0); %% The left bar: penpos1(thin, 0); z1 = (1/2, 1/4) uu; penpos2(med, 180); z2r = (0, 1/5) uu; penpos3(med, 300); z3r = (1/2, 0) uu; penpos4(med, 0); z4l = (1, 1) uu; penstroke z1e{up} .. {down}z2e .. z3e .. tension 1.6 .. {up}z4e; %% The middle bar: penpos5(med, 180); z5r = z4l; penpos6(thick, 180); z6 = (3/2, 0) uu; penstroke z5e .. z6e; %% The right bar: penpos7(med, 0); z7r = z6l; penpos8(med, 290); z8l = (7/3, 1) uu; penpos9(med, 180); z9l = (3, 2/3) uu; penpos10(med, 90); z10 = (5/2, 1/3) uu; penpos11(thin, 0); z11 = (2, 2/3) uu; penstroke z7e{up} .. tension 1.2 .. z8e .. {down}z9e .. z10e .. {dir 70}z11e; label(11); save_letter(N)(x6); endchar; "The letter O"; beginchar("O", ltr_wd(2,0), hgt, 0); penpos1(thin, 90); z1r = (9/8, 1) uu; penpos2(thick, 180); z2r = (0, 1/2) uu; penpos3(med, 270); z3r = (1, 0) uu; penpos4(thick, 0); z4r = (2, 1/2) uu; penpos5(med, 90); z5r = (6/5, 19/20) uu; penpos6(thin, 180); z6 = (1/2, 1/3) uu; penstroke z1e{left} .. z2e .. z3e .. z4e .. z5e .. {dir 300}z6e; label(6); save_letter(O)(x3); endchar; "The letter P"; beginchar("P", ltr_wd(5/2,0), hgt, 0); penpos1(thin, 180); z1r = (3/2, 1) uu; penpos2(thick, 180); z2 = (3/2, 1/2) uu; penpos3(med, 90); z3l = (1, 0) uu; penpos4(thin, 0); z4 = (1/2, 1/4) uu; penstroke z1e .. z2e .. z3e .. z4e; penpos5(thin, 180); z5 = (1, 2/3) uu; penpos6(med, 90); z6 = (1/2, 1/3) uu; penpos7(med, 0); z7l = (0, 1/2) uu; penpos8(med, 270); z8l = (4/3, 1) uu; penpos9(thick, 180); z9l = (5/2, 3/4) uu; penpos10(thin, 0); z10 = (5/3, 3/4) uu; penstroke z5e .. z6e .. z7e{up} .. z8e .. z9e{down} .. z10e; label(10); endchar; "The letter Q"; beginchar("Q", ltr_wd(5/2,0), hgt, thick#/2); addto currentpicture also letter.O; penpos1(thin, 270); z1 = (4/5, 1/6) uu; penpos2(thick, 270); z2 = (2, 0) uu; penpos3(med, 0); z3r = (5/2, 1/8) uu; penpos4(thin, 90); z4 = (13/6, 1/4) uu; penstroke z1e{dir 20} .. z2e .. z3e .. z4e; label(4); endchar; "The letter R"; beginchar("R", ltr_wd(13/4,0), hgt, 0); penpos1(thin, 180); z1r = (3/2, 1) uu; penpos2(thick, 180); z2 = (3/2, 1/2) uu; penpos3(med, 90); z3l = (1, 0) uu; penpos4(thin, 0); z4 = (1/2, 1/4) uu; penstroke z1e .. z2e .. z3e .. z4e; penpos5(thin, 180); z5 = (1, 2/3) uu; penpos6(med, 90); z6 = (1/2, 1/3) uu; penpos7(med, 0); z7l = (0, 1/2) uu; penpos8(med, 270); z8l = (4/3, 1) uu; penpos9(thick, 180); z9 = (5/2, 3/4) uu; penpos10(med, 345); z10 = (5/3, 3/5) uu; penpos11(thick, 180); z11 = (7/3, 1/3) uu; penpos12(med, 270); z12r = (11/4, 0) uu; penpos13(med, 0); z13r = (13/4, 1/6) uu; penpos14(thin, 90); z14 = (11/4, 1/3) uu; penstroke z5e .. z6e .. z7e{up} .. z8e .. z9e .. tension 1.2 .. z10e{up} .. tension 1.4 .. z11e .. z12e .. z13e .. z14e; label(14); save_letter(R)(x10); endchar; "The letter S"; beginchar("S", ltr_wd(2,0), hgt, 0); penpos1(thin, 180); z1 = (2/5, 1) uu; penpos2(med, 180); z2r = (0, 2/3) uu; penpos3(med, 270); z3 = (1, 1/2) uu; penpos4(med, 0); z4r = (2, 5/6) uu; penpos5(med, 90); z5r = (8/5, 1) uu; penpos6(thick, 210); z6r = (1, 1/3) uu; penpos7(med, 90); z7l = (1, 0) uu; penpos8(med, 70); z8 = (2/5, 1/4) u; penpos9(thin, 180); z9r = (0, 0) uu; penstroke z1e .. {down}z2e .. z3e .. z4e .. z5e .. z6e .. z7e .. z8e .. {dir 250}z9e; label(9); save_letter(S)(1/2[x3,x5]); cedpos.S := x7; endchar; "The letter T"; beginchar("T", ltr_wd(11/4,0), hgt, 0); penpos1(thin, 180); z1 = (1, 2/3) uu; penpos2(med, 0); z2l = (0, 7/10) uu; penpos3(med, 270); z3l = (2/3, 1) uu; penpos4(thick, 200); z4 = (13/8, 2/3) uu; penpos5(med, 0); z5r = (11/4, 3/4) uu; penpos6(med, 90); z6r = (17/8, 1) uu; penpos7(thick, 180); z7 = (9/8, 2/5) uu; penpos8(med, 270); z8r = (2, 0) uu; penpos9(med, 0); z9r = (5/2, 1/6) uu; penpos10(thin, 180); z10 = (7/4, 1/4) uu; penstroke z1e{down} .. {up}z2e .. z3e .. {dir 300}z4e .. z5e .. {left}z6e .. tension 1.2 .. z7e .. {right}z8e .. z9e .. z10e; label(10); save_letter(T)(1/2[x3,x6]); cedpos.T := x8; endchar; "The letter U"; beginchar("U", ltr_wd(3,0), hgt, 0); penpos1(thin, 180); z1 = (3/4, 3/5) uu; penpos2(med, 0); z2l = (0, 2/3) uu; penpos3(med, 250); z3l = (3/5, 1) uu; penpos4(thick, 180); z4 = (1, 1/4) uu; penpos5(med, 270); z5r = (3/2, 0) uu; penpos6(med, 0); z6 = (2, 1/6) uu; penstroke z1e{down} .. z2e{up} .. z3e .. tension 1.1 .. z4e .. z5e .. z6e; penpos7(med, 180); z7 = (2, 1) uu; penpos8(thick, 180); z8 = z6; penpos9(med, 270); z9r = (5/2, 0) uu; penpos10(med, 0); z10r = (3, 1/6) uu; penpos11(thin, 90); z11 = (12/5, 1/3) uu; penstroke z7e{down} .. z8e{dir 280} .. z9e .. z10e .. z11e; label(11); save_letter(U)(1/2[x4,x7]); endchar; "The letter V"; beginchar("V", ltr_wd(8/3,0), hgt, 0); penpos1(thin, 180); z1 = (3/4, 3/5) uu; penpos2(med, 0); z2l = (0, 2/3) uu; penpos3(med, 250); z3l = (3/5, 1) uu; penpos4(thick, 180); z4 = (1, 1/4) uu; penpos5(med, 270); z5r = (3/2, 0) uu; penpos6(med, 0); z6 = (9/4, 1/2) uu; penpos7(med, 90); z7r = (11/6, 1) uu; penpos8(med, 270); z8 = (2, 2/3) uu; penpos9(thin, 0); z9r = (8/3, 1) uu; penstroke z1e{down} .. z2e{up} .. z3e .. tension 1.1 .. z4e .. z5e .. {up}z6e .. tension 1.3 .. z7e{left} .. {right}z8e .. {up}z9e; label(9); endchar; "The letter W"; beginchar("W", ltr_wd(11/3,0), hgt, 0); penpos1(thin, 180); z1 = (3/4, 3/5) uu; penpos2(med, 0); z2l = (0, 2/3) uu; penpos3(med, 250); z3l = (3/5, 1) uu; penpos4(thick, 180); z4 = (1, 1/4) uu; penpos5(med, 270); z5r = (3/2, 0) uu; penpos6(med, 0); z6 = (2, 1/6) uu; penstroke z1e{down} .. z2e{up} .. z3e .. tension 1.1 .. z4e .. z5e .. z6e; penpos7(med, 180); z7 = (15/8, 7/8) uu; penpos8(thick, 180); z8 = z6; penpos9(med, 270); z9r = (5/2, 0) uu; penpos10(med, 0); z10 = (13/4, 1/2) uu; penpos11(med, 90); z11r = (17/6, 1) uu; penpos12(med, 270); z12 = (3, 2/3) uu; penpos13(thin, 0); z13r = (11/3, 1) uu; penstroke z7e{down} .. z8e{dir 280} .. z9e .. {up}z10e .. tension 1.3 .. z11e{left} .. {right}z12e .. {up}z13e; label(13); endchar; "The letter X"; beginchar("X", ltr_wd(8/3,0), hgt, 0); penpos1(thin, 90); z1 = (2/3, 2/3) uu; penpos2(med, 0); z2l = (0, 5/6) uu; penpos3(med, 270); z3l = (2/3, 1) uu; penpos4(thick, 180); z4 = (4/3, 1/2) uu; penpos5(med, 90); z5l = (1/2, 0) uu; penpos6(med, 0); z6l = (0, 1/6) uu; penpos7(thin, 270); z7 = (1/3, 1/3) uu; penstroke z1e .. z2e .. z3e .. z4e .. z5e .. z6e .. z7e; penpos8(thin, 270); z8 = (2, 1/3) uu; penpos9(med, 180); z9l = (8/3, 1/6) uu; penpos10(med, 90); z10l = (2, 0) uu; penpos11(thick, 0); z11 = (4/3, 1/2) uu; penpos12(med, 270); z12l = (13/6, 1) uu; penpos13(med, 180); z13l = (8/3, 5/6) uu; penpos14(thin, 90); z14 = (7/3, 2/3) uu; penstroke z8e .. z9e .. z10e .. z11e .. z12e .. z13e .. z14e; label(14); endchar; "The letter Y"; beginchar("Y", ltr_w(19/8), hgt, loop_descend * ex#); penpos1(thin, 180); z1 = (3/4, 3/5) uu; penpos2(med, 0); z2l = (0, 2/3) uu; penpos3(med, 250); z3l = (3/5, 1) uu; penpos4(thick, 180); z4 = (1, 3/8) uu; penpos5(med, 270); z5r = (3/2, 1/8) uu; penpos6(med, 0); z6l = z8r; penpos7(thick, 180); x7 = x8; y7 = uc_ascend * ex; penpos8(thick, 180); z8 = good.rt ((9/4, 1) u); penstroke z1e{down} .. z2e{up} .. z3e .. tension 1.1 .. z4e .. z5e .. {up}z6e; penstroke z7e .. z8e; addto currentpicture also letter.j shifted (3/2 * v, 0); label(8); save_letter(Y)(1/2[x4,x7]); endchar; "The letter Z"; beginchar("Z", ltr_wd(3,0), hgt, 0); penpos1(thin, 180); z1 = (3/4, 5/6) uu; penpos2(med, 0); z2l = (0, 3/4) uu; penpos3(med, 270); z3l = (1/2, 1) uu; penpos4(med, 270); z4 = (5/2, 3/4) uu; penpos5(med, 0); z5r = (3, 7/8) uu; penpos6(med, 90); z6r = (8/3, 1) uu; penpos7(thick, 165); z7 = (6/4, 1/2) uu; penpos8(med, 90); z7 = 1/2[z6, z8]; penpos9(med, 0); z7 = 1/2[z5, z9]; penpos10(med, 270); z7 = 1/2[z4, z10]; penpos11(med, 270); z7 = 1/2[z3, z11]; penpos12(med, 0); z7 = 1/2[z2, z12]; penpos13(thin, 180); z7 = 1/2[z1, z13]; penstroke z1e .. z2e{up} .. z3e{right} .. z4e .. z5e{up} .. z6e{left} .. z7e .. {left}z8e .. z9e .. z10e .. {right}z11e .. z12e{up} .. z13e; penpos14(thin, 270); z14 = z7 - (1/2, 0) uu; penpos15(med, 270); z15 = z7; penpos16(thin, 270); z16 = z7 + (1/2, 0) uu; penstroke z14e{dir 30} .. z15e .. {dir 30}z16e; label(16); save_letter(Z)(x15); endchar; %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %%\sec Inter-letter links. %{{{1 %% The constants below define the position of the link glyphs in the font. %% the names have the form ``{\it lnk.right.left}'' where {\it right} is the %% shape of the letter on the right and {\it left} is the kind of link at the %% end of the letter on the left. %% Since we are limited to 256 positions, we have to use some codes that are %% defined in the T1 encoding for other purposes. The accent glyphs may be %% used for that, since constructed accented letters are unusable in this font %% (because they don't link to surrounding letters). The ``f'' ligatures are %% also usable since they are irrelevant here. lnk.small.low = 0; lnk.small.med = 1; lnk.small.high = 2; lnk.loop.low = 3; lnk.loop.med = 4; lnk.loop.high = 5; lnk.vert.low = 6; lnk.vert.med = 7; lnk.vert.high = 8; lnk.far.low = 9; lnk.far.med = 10; lnk.far.high = 11; lnk.hloop.low = 12; lnk.hloop.med = 13; lnk.mn.low = 14; lnk.mn.med = 15; lnk.mn.high = 16; lnk.mn.beg = 17; lnk.x.low = 24; lnk.x.med = 27; lnk.sq = 28; lnk.high = 29; lnk.low = 30; lnk.lowmed = 31; %% There is a special trick we use in all links: the initial $x$ coordinante %% is not 0 as would be expected but $-1$. This makes links begin one pixel to %% the left of their box, ensuring that they actually join with the letter %% before them. lw := link_width * ex#; %%\subsec For small letters (a, c, d, e, g, o, q). %{{{2 "Low link for small letters"; beginchar(lnk.small.low, lw, 0, 0); penpos1(med, 270); z1r = (-1, 0); penpos2(med, 0); z2l = (lnk, 1/3) u; penstroke z1e{right} .. {up}z2e; label(2); endchar ; "Medium link for small letters"; beginchar(lnk.small.med, lw, 0, 0); penpos1(med, ml_d); z1 = (-1, ml_y * ex); penpos2(med, ml_d); z2l = (lnk, 1/3) u; penstroke z1e{ml_dir} .. tension 3 .. {up}z2e; label(2); endchar ; "High link for small letters"; beginchar(lnk.small.high, lw, 0, 0); penpos1(med, 270); z1 = (-1, hl_y * ex); penpos2(thin, 270); z2l = (3/5 + lnk, 1) u; penstroke z1e{right} .. {right}z2e ; label(2); endchar ; %%\subsec For loops (b, f, h, l). %{{{2 "Low link for large loops"; beginchar(lnk.loop.low, lw, loop_ascend*ex#, 0); if proofing > 1: proofrule ((lnk,0) u, (lnk,loop_ascend)u); fi penpos1(med, 270); z1r = (-1, 0); penpos2(med, 330); z2 = (3/4 + lnk, 2/3 * loop_ascend) u + (0,0); penstroke z1e{right} .. tension 2 .. {up}z2e ; label(2); endchar; "Medium link for large loops"; beginchar(lnk.loop.med, lw, loop_ascend*ex#, 0); if proofing > 1: proofrule ((lnk,0) u, (lnk,loop_ascend)u); fi penpos1(med, ml_d); z1 = (-1, ml_y * ex); penpos2(med, 330); z2 = (3/4 + lnk, 2/3 * loop_ascend) u + (0,0); penstroke z1e{ml_dir} .. tension 1.2 .. {up}z2e ; label(2); endchar; "High link for large loops"; beginchar(lnk.loop.high, lw, loop_ascend*ex#, 0); if proofing > 1: proofrule ((lnk,0) u, (lnk,loop_ascend)u); fi penpos1(med, 270); z1 = (-1, hl_y * ex); penpos2(med, 330); z2 = (3/4 + lnk, 2/3 * loop_ascend) u + (0,0); penstroke z1e{right} .. tension 1.4 .. {up}z2e ; label(2); endchar; "Low to medium transition"; beginchar(lnk.lowmed, ltr_w(1/6), 0, 0); penpos1(med, 270); z1r = (-1, 0); penpos2(med, ml_d); z2 = (1/6 + lnk, ml_y) u; penstroke z1e{right} .. {ml_dir}z2e ; label(2); endchar; %%\subsec For those vertical on the left (i, u). %{{{2 "Low link for verticals"; beginchar(lnk.vert.low, lw, 0, 0); penpos1(med, 270); z1r = (-1, 0); penpos2(med, 0); z2l = (1/6 + lnk, 2/3) u; penpos3(med, 0); z3l = (1/6 + lnk, 1) u; penstroke z1e{right} .. {up}z2e -- z3e; label(3); endchar; "Medium link for verticals"; beginchar(lnk.vert.med, lw, 0, 0); penpos1(med, ml_d); z1 = (-1, ml_y * ex); penpos2(med, 0); z2l = (1/6 + lnk, 1) u; penstroke z1e{ml_dir} .. tension 1.2 .. {up}z2e; label(2); endchar; "High link for verticals"; beginchar(lnk.vert.high, lw, 0, 0); penpos1(med, 270); z1 = (-1, hl_y * ex); penpos2(med, 0); z2l = (1/6 + lnk, 1) u; penstroke z1e{right} .. {up}z2e; label(2); endchar; %%\subsec For the far verticals (j, p). %{{{2 "Low link for far verticals"; beginchar(lnk.far.low, lw, 0, 0); penpos1(med, 270); z1r = (-1, 0); penpos2(med, 0); z2l = z3l; pickup thickpen; penpos3(thick, 0); z3 = good.rt ((3/4 + lnk, 1) u); penstroke z1e{right} .. tension 1.2 .. {dir 60}z2e; label(2); endchar; "Medium link for far verticals"; beginchar(lnk.far.med, ltr_w(-1/4), 0, 0); penpos1(med, ml_d); z1 = (-1, ml_y * ex); penpos2(med, 0); z2l = z3l; penpos3(thick, 0); z3 = good.rt ((1/2 + lnk, 1) u); penstroke z1e{ml_dir} .. tension 1.3 .. {dir 60}z2e; label(2); endchar; "High link for far verticals"; beginchar(lnk.far.high, ltr_w(-1/4), 0, 0); penpos1(med, 270); z1 = (-1, hl_y * ex); penpos2(med, 0); z2l = z3l; penpos3(thick, 0); z3 = good.rt ((1/2 + lnk, 1) u); penstroke z1e{right} .. {dir 50}z2e; label(2); endchar; %%\subsec For high loops (h, k). %{{{2 "Low link for high loops"; beginchar(lnk.hloop.low, ltr_w(1/6), 0, 0) penpos1(med, 270); z1r = (-1, 0); penpos2(med, 0); z2l = (1/6 + lnk, 6/8) u; penstroke z1e{right} .. {up}z2e; penpos3(med, 270); z3l = z2l; penpos4(med, 330); z4 = (11/12 + lnk, 2/3 * loop_ascend) u + (0,0); penstroke z3e .. tension 1.2 .. {up}z4e; label(4); endchar; "Medium link for high loops"; beginchar(lnk.hloop.med, lw, 0, 0) penpos1(med, ml_d); z1 = (-1, ml_y * ex); penpos2(med, 0); z2l = (lnk, 6/8) u; penstroke z1e{ml_dir} .. {up}z2e; penpos3(med, 270); z3l = z2l; penpos4(med, 330); z4 = (3/4 + lnk, 2/3 * loop_ascend) u + (0,0); penstroke z3e .. tension 1.2 .. {up}z4e; label(4); endchar; %%\subsec For m, n, v, and w. %{{{2 "Low link for m and n"; beginchar(lnk.mn.low, ltr_w(1/6), 0, 0) penpos1(med, 270); z1r = (-1, 0); penpos2(med, 0); z2l = (1/12 + lnk, 1/2) u; penpos3(med, 270); z3l = (1/2 + lnk, 1) u + (1,0); penstroke z1e{right} .. tension 1.4 .. {up}z2e .. {right}z3e; label(3); endchar; "Medium link for m and n"; beginchar(lnk.mn.med, ltr_w(1/12), 0, 0) penpos1(med, ml_d); z1 = (-1, ml_y * ex); penpos2(med, 0); z2l = ((1/24 + lnk) * v, 1/2 [y1, y3]); penpos3(med, 270); z3l = (5/12 + lnk, 1) u + (1,0); penstroke z1e{ml_dir} .. {up}z2e .. tension 1.1 .. {right}z3e; label(3); endchar; "High link for m and n"; beginchar(lnk.mn.high, ltr_w(1/6), 0, 0) penpos1(med, 270); z1 = (-1, hl_y * ex); penpos2(med, 330); z2 = 1/2 [z1, z3]; penpos3(med, 270); z3l = (1/2 + lnk, 1) u + (1,0); penstroke z1e{right} .. z2e .. {right}z3e; label(3); endchar; "Beginning for m and n"; beginchar(lnk.mn.beg, 0, 0, 0) penpos1(med, 320); z1 = (-1, 2/5 * ex); penpos2(med, 270); z2l = (1/3, 1) u + (1,0); penstroke z1e{up} .. {right} z2e; label(3); endchar; %%\subsec For the x. %{{{2 "Low link for x"; beginchar(lnk.x.low, ltr_w(1/2), 0, 0) penpos1(med, 270); z1r = (-1, 0); penpos2(med, 0); z2 = 1/2[z1,z3]; penpos3(med, 270); z3l = (5/6 + lnk, 1) u + (1,0); penstroke z1e{right} .. {dir 80}z2e .. {right}z3e; label(3); endchar; "Medium link for x"; beginchar(lnk.x.med, ltr_w(1/4), 0, 0) penpos1(med, ml_d); z1 = (-1, ml_y * ex); penpos2(med, 0); z2 = 1/2[z1,z3]; penpos3(med, 270); z3l = (7/12 + lnk, 1) u + (1,0); penstroke z1e{ml_dir} .. {dir 80}z2e .. {right}z3e; label(3); endchar; %%\subsec Special links. %{{{2 %% The letters {\fc s} and {\fc q} have final forms without a link on the %% right, which is the actual glyph. Inside words, they need an extra link. "Right link for s and q"; beginchar(lnk.sq, lw, ex#/3, 0); penpos1(med, 180); z1l = (0, 1/3) u; penpos2(med, 270); z2r = (lnk, 0) u; penstroke z1e {down} .. {right}z2e; label(2); endchar; %% \chardef\HL=131 %% This link has to be inserted by hand between the letters {\fc o} and %% {\fc e}, in order to produce ``{\fc o\HL e}'', which is different %% from the (fake) ligature ``{\fc oe}'' that is produced by typing %% ``{\tt oe}''. "High horizontal link"; beginchar(lnk.high, lw, 0, 0); penpos1(med, 270); z1 = (-1, hl_y * ex); penpos2(med, 270); z2 = (lnk, 1/2) u + (1,0); penstroke z1e{right} .. {right}z2e ; label(2); endchar ; %% This one is the equivalent but at the level of the baseline. It is %% introduced for coherence. %% \par\nobreak "Low horizontal link"; beginchar(lnk.low, lw, 0, 0); penpos1(med, 270); z1r = (-1, 0); penpos2(med, 270); z2r = (lnk * v + 1, 0); penstroke z1e{right} .. {right}z2e ; label(2); endchar ; %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %%\sec Accents and accented letters. %{{{1 %% These constants are reference dimensions for all accents: a_wd := accent_wd * base_width * ex#; a_ht := accent_top * ex#; %%\subsec The glyphs for the accents. %{{{2 %% When \TeX\ builds an accented character out of an unaccented one and an %% accent glyph, the resulting object is not subject to ligatures. Therefore %% the accent glyphs are rather useless in this font, which has the pleasant %% effect of freeing a good number of character positions. The glyphs below %% are thus drawn, but not saved (except for some of them that correspond to %% proper characters, like tilde or circumflex). We use the following macros %% to save an accent's picture and dimensions in order to use it later when %% building accented characters: %%% beginchar beginaccent %%% endchar endaccent ignored = 0; def beginaccent (expr code, wd, ht, dp) = beginchar(code, wd, ht, dp); enddef; def endaccent (suffix acc) = picture accent.acc; accent.acc := currentpicture; acc_wd.acc := w; acc_ht#.acc := charht; acc_dp#.acc := chardp; if charcode = ignored: save shipit; let shipit = relax; fi endchar enddef; athin := 2/3 [thin, med]; athick := 2/3 [med, thick]; "Grave accent"; beginaccent(ignored, a_wd, a_ht, 0); penpos1(athick, 225); z1 = (0, 1) ua; penpos2(athin, 270); z2 = (1, 0) ua; penstroke z1e .. tension 1.4 .. {right}z2e; label(2); endaccent(grave); "Acute accent"; beginaccent(ignored, a_wd, a_ht, 0); penpos1(athick, 135); z1 = (1, 1) ua; penpos2(athin, 90); z2 = (0, 0) ua; penstroke z1e .. tension 1.4 .. {left}z2e; label(2); endaccent(acute); "Circumflex"; beginaccent("^", 3/2 * a_wd, a_ht, 0); penpos1(athin, 270); z1 = (0, 0) ua; penpos2(athick, 0); z2 = (3/4, 1) ua; penstroke z1e{right} .. z2e; penpos3(athick, 180); z3 = z2; penpos4(athin, 270); z4 = (3/2, 0) ua; penstroke z3e .. {right}z4e; label(4); endaccent(circum); "Tilde"; beginaccent("~", 3/2 * a_wd, (2 accent_top + accent_bot)/3 * ex#, 0); penpos1(athin, 310); z1 = (0, 1/3) ua; penpos2(med, 210); z2l = (3/4, 1/2) ua; penpos4(athick, 310); (x4, y4l) = (3/2, 2/3) ua; penstroke z1e .. z2e{dir 315} .. z4e; label(4); endaccent(tilde); "Double acute"; beginaccent(34, 4/3 a_wd, a_ht, 0); penpos1(athick, 135); z1 = (2/3, 1) ua; penpos2(athin, 135); z2 = (0, 0) ua; penstroke z1e .. z2e; z3 = (4/3, 1) ua; addto currentpicture also currentpicture shifted (z3 - z1); label(2); endaccent(dblacute); "Umlaut"; beginaccent(ignored, a_wd, height_with_dot, 0); pickup pencircle scaled dot_size; lft z1 = (0, dot_height) u; rt z2 = (accent_wd, dot_height) u; drawdot z1; drawdot z2; label(2); endaccent(umlaut); "Ring"; beginaccent(ignored, 3/4 a_wd, a_ht, 0); penpos1(med, 90); z1r = (3/8, 1) ua; penpos2(med, 180); z2r = (0, 1/2) ua; penpos3(med, 270); z3r = (3/8, 0) ua; penpos4(med, 0); z4r = (3/4, 1/2) ua; penstroke z1e .. z2e .. z3e .. z4e .. cycle; label(4); endaccent(ring); "Hachek"; beginaccent(ignored, 3/2 * a_wd, a_ht, 0); penpos1(athin, 270); z1l = (0, 1) ua; penpos2(athick, 270); z2r = (3/4, 0) ua; penpos3(athin, 270); z3l = (3/2, 1) ua; penstroke z1e -- z2e -- z3e; label(3); endaccent(hachek); "Breve"; beginaccent(ignored, 3/2 * a_wd, a_ht, 0); penpos1(athin, 180); z1r = (0, 1) ua; penpos2(med, 270); z2r = (3/4, 0) ua; penpos3(athin, 0); z3r = (3/2, 1) ua; penstroke z1e .. z2e .. z3e; label(3); endaccent(breve); "Cedilla"; beginaccent(ignored, ltr_wd(3/4,0), 0, (cedilla_dp + 1/3) * ex#); penpos1(thick, 180); z1 = (3/8, 0) u; penpos2(thick, 180); z2 = (3/8, -cedilla_dp) u; penstroke z1e .. z2e; penpos3(med, 270); z3r = z2l; penpos4(athick, 180); x4l = 3/4 base_width * ex; y4 = 1/2[y3,y5]; penpos5(med, 90); z5l = (3/8, -cedilla_dp - 1/3) u; penpos6(athin, 0); x6l = 0; y6 = y4; penstroke z3e .. z4e .. z5e{left} .. z6e; label(6); endaccent(cedilla); "Ogonek"; beginaccent(ignored, ltr_wd(3/4,0), 0, 2 * cedilla_dp * ex#); penpos1(med, 90); z1l = (3/8, 0) u; penpos2(athick, 180); z2r = (0, -cedilla_dp) u; penpos3(med, 270); z3r = (3/8, -2 cedilla_dp) u; penpos4(athin, -45); z4 = (0.7, -cedilla_dp) u; penstroke z1e {left} .. z2e .. z3e .. z4e; label(4); endaccent(ogonek); %%\subsec The accented characters. %{{{2 %% The definition of `make\_accented' produces characters with the same height %% as their unaccented version, so that the accented uppercase are not too %% high (otherwise it would force to space out successive lines too much). %% The macro `make\_cedilla' is used to put something (a cedilla or an %% ogonek) under a letter, and this one does modify the depth of the original %% letter. The macro `make\_caron' adds a caron (same shape as an apostrophe) %% to a glyph, without changing the glyph width, so that linking is not %% influenced. def make_accented(expr name, chr)(text base, acc) = begingroup save base; name; beginchar(chr, width#.base, height#.base, depth#.base) addto currentpicture also letter.base; addto currentpicture also accent.acc shifted ((accpos.base - acc_wd.acc/2, height.base - ex) slanted slant); endchar endgroup enddef; def make_cedilla(expr name, chr)(text base, acc) = begingroup save base; name; beginchar(chr, width#.base, height#.base, max(depth#.base, acc_dp#.acc)) addto currentpicture also letter.base; addto currentpicture also accent.acc shifted (cedpos.base - acc_wd.acc/2, 0); endchar endgroup enddef; def make_caron(expr name, chr)(text base, pos) = begingroup save base; name; beginchar(chr, width#.base, height#.base, depth#.base) addto currentpicture also letter.base; penpos1(athick, 180); penpos2(athin, 90); y1 = h; x2 = pos; z1 - z2 = (accent_wd/2, 1/2) u; penstroke z1e {down} .. z2e; label(2); endchar endgroup enddef; make_accented("The letter a with breve", 160)(a)(breve); make_cedilla ("The letter a with ogonek", 161)(a)(ogonek); make_accented("The letter a with gravis", 224)(a)(grave); make_accented("The letter a with acute", 225)(a)(acute); make_accented("The letter a with circumflex", 226)(a)(circum); make_accented("The letter a with tilde", 227)(a)(tilde); make_accented("The letter a with umlaut", 228)(a)(umlaut); make_accented("The letter a with ring", 229)(a)(ring); make_accented("The letter c with acute", 162)(c)(acute); make_accented("The letter c with hachek", 163)(c)(hachek); make_cedilla ("The letter c with cedilla", 231)(c)(cedilla); make_caron("The letter d with caron", 164)(d)(accpos.d + thick*base_width); make_accented("The letter e with hachek", 165)(e)(hachek); make_cedilla ("The letter e with ogonek", 166)(e)(ogonek); make_accented("The letter e with gravis", 232)(e)(grave); make_accented("The letter e with acute", 233)(e)(acute); make_accented("The letter e with circumflex", 234)(e)(circum); make_accented("The letter e with umlaut", 235)(e)(umlaut); make_accented("The letter g with breve", 167)(g)(breve); make_accented("The letter i with gravis", 236)(i)(grave); make_accented("The letter i with acute", 237)(i)(acute); make_accented("The letter i with circumflex", 238)(i)(circum); make_accented("The letter i with umlaut", 239)(i)(umlaut); make_accented("The letter l with acute", 168)(l)(acute); make_caron ("The letter l with caron", 169)(l)(w); "The letter l slash"; beginchar(170, width#.l, height#.l, depth#.l) addto currentpicture also letter.l; penpos1(med, 270); penpos2(med, 270); penpos3(thick, 0); z3l = (0, loop_ascend/2) u; 1/2[z2,z1] = z3; z2 - z1 = (2/3, 1/6) u; penstroke z1e .. z2e; label(2); endchar; make_accented("The letter n with acute", 171)(n)(acute); make_accented("The letter n with hachek", 172)(n)(hachek); make_accented("The letter n with tilde", 241)(n)(tilde); make_accented("The letter o with double acute", 174)(o)(dblacute); make_accented("The letter o with gravis", 242)(o)(grave); make_accented("The letter o with acute", 243)(o)(acute); make_accented("The letter o with circumflex", 244)(o)(circum); make_accented("The letter o with tilde", 245)(o)(tilde); make_accented("The letter o with umlaut", 246)(o)(umlaut); "Scandinavian letter o slash"; beginchar(248, width#.o, 7/6 ex#, 1/6 ex#) addto currentpicture also letter.o; penpos1(med, 150); z1l = (w, 7/6 ex); penpos2(med, 150); z2r = (0, -1/6 ex); penstroke z1e .. z2e; label(2); endchar; make_accented("The letter r with acute", 175)(r)(acute); make_accented("The letter r with hachek", 176)(r)(hachek); make_accented("The letter s with acute", 177)(s)(acute); make_accented("The letter s with hachek", 178)(s)(hachek); make_cedilla ("The letter s with cedilla", 179)(s)(cedilla); make_caron ("The letter t with caron", 180)(t)(accpos.t); make_cedilla ("The letter t with cedilla", 181)(t)(cedilla); make_accented("The letter u with double acute", 182)(u)(dblacute); make_accented("The letter u with ring", 183)(u)(ring); make_accented("The letter u with gravis", 249)(u)(grave); make_accented("The letter u with acute", 250)(u)(acute); make_accented("The letter u with circumflex", 251)(u)(circum); make_accented("The letter u with umlaut", 252)(u)(umlaut); make_accented("The letter y with umlaut", 184)(y)(umlaut); make_accented("The letter y with acute", 253)(y)(acute); make_accented("The letter z with acute", 185)(z)(acute); make_accented("The letter z with hachek", 186)(z)(hachek); "The letter z with dot above"; beginchar(187, width#.z, height#.z, depth#.z) addto currentpicture also letter.z; pickup pencircle scaled dot_size; drawdot (accpos.z, 1/2[accent_bot, accent_top] * ex); endchar; make_accented("The letter A with breve", 128)(A)(breve); make_cedilla ("The letter A with ogonek", 129)(A)(ogonek); make_accented("The letter A with gravis", 192)(A)(grave); make_accented("The letter A with acute", 193)(A)(acute); make_accented("The letter A with circumflex", 194)(A)(circum); make_accented("The letter A with tilde", 195)(A)(tilde); make_accented("The letter A with umlaut", 196)(A)(umlaut); make_accented("The letter A with ring", 197)(A)(ring); make_accented("The letter C with acute", 130)(C)(acute); make_accented("The letter C with hachek", 131)(C)(hachek); make_cedilla ("The letter C with cedilla", 199)(C)(cedilla); make_accented("The letter D with hachek", 132)(D)(hachek); make_accented("The letter E with hachek", 133)(E)(hachek); make_cedilla ("The letter E with ogonek", 134)(E)(ogonek); make_accented("The letter E with gravis", 200)(E)(grave); make_accented("The letter E with acute", 201)(E)(acute); make_accented("The letter E with circumflex", 202)(E)(circum); make_accented("The letter E with umlaut", 203)(E)(umlaut); make_accented("The letter G with breve", 135)(G)(breve); "The letter I with dot above"; beginchar(157, width#.I, height#.I, depth#.I) addto currentpicture also letter.I; pickup pencircle scaled dot_size; drawdot (accpos.z, (1/2[accent_bot, accent_top] + uc_ascend - 1) * ex); endchar; make_accented("The letter I with gravis", 204)(I)(grave); make_accented("The letter I with acute", 205)(I)(acute); make_accented("The letter I with circumflex", 206)(I)(circum); make_accented("The letter I with umlaut", 207)(I)(umlaut); make_accented("The letter L with acute", 136)(L)(acute); make_caron ("The letter L with caron", 137)(L)(w); "The letter L slash"; beginchar(138, width#.L, height#.L, depth#.L) addto currentpicture also letter.L; penpos1(med, 270); penpos2(med, 270); 1/2[z2,z1] = (7/6, 2/5) uu; z2 - z1 = (1, 1/10) u; penstroke z1e .. z2e; label(2); endchar; make_accented("The letter N with acute", 139)(N)(acute); make_accented("The letter N with hachek", 140)(N)(hachek); make_accented("The letter N with tilde", 209)(N)(tilde); make_accented("The letter O with double acute", 142)(O)(dblacute); make_accented("The letter O with gravis", 210)(O)(grave); make_accented("The letter O with acute", 211)(O)(acute); make_accented("The letter O with circumflex", 212)(O)(circum); make_accented("The letter O with tilde", 213)(O)(tilde); make_accented("The letter O with umlaut", 214)(O)(umlaut); "Scandinavian letter O slash"; beginchar(216, width#.O, height#.O, depth#.O) addto currentpicture also letter.O; penpos1(med, 150); z1l = (w - 1/8 v, h); penpos2(med, 150); z2r = (1/8 v, 0); penstroke z1e .. z2e; label(2); endchar; make_accented("The letter R with acute", 143)(R)(acute); make_accented("The letter R with hachek", 144)(R)(hachek); make_accented("The letter S with acute", 145)(S)(acute); make_accented("The letter S with hachek", 146)(S)(hachek); accpos.S := base_width * ex; make_cedilla ("The letter S with cedilla", 147)(S)(cedilla); make_accented("The letter T with hachek", 148)(T)(hachek); accpos.T := 2 base_width * ex; make_cedilla ("The letter T with cedilla", 149)(T)(cedilla); make_accented("The letter U with double acute", 150)(U)(dblacute); make_accented("The letter U with ring", 151)(U)(ring); make_accented("The letter U with gravis", 217)(U)(grave); make_accented("The letter U with acute", 218)(U)(acute); make_accented("The letter U with circumflex", 219)(U)(circum); make_accented("The letter U with umlaut", 220)(U)(umlaut); make_accented("The letter Y with umlaut", 152)(Y)(umlaut); make_accented("The letter Y with acute", 221)(Y)(acute); make_accented("The letter Z with acute", 153)(Z)(acute); make_accented("The letter Z with hachek", 154)(Z)(hachek); "The letter Z with dot above"; beginchar(155, width#.Z, height#.Z, depth#.Z) addto currentpicture also letter.Z; pickup pencircle scaled dot_size; drawdot (accpos.Z, (1/2[accent_bot, accent_top] + uc_ascend - 1) * ex); endchar; "The letter i with no dot"; beginchar(25, width#.i, ex#, 0); addto currentpicture also letter.i; endchar; "The letter j with no dot"; beginchar(26, width#.j, ex#, loop_descend * ex#); addto currentpicture also letter.j; endchar; %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %%\sec Digits. %{{{1 %% All digits have the same height, fixed to $\frac3/2\,\\{base\_witdh}$, and %% they contain an extra spacing of $\frac1/6\,\\{base\_width}$ on each side. num_wd := 11/6 * base_width * ex#; num_ht := straight_ascend * ex#; def nu = shifted (1/6,0) u yscaled straight_ascend enddef; "The numeral 0"; beginchar("0", num_wd, num_ht, 0); penpos1(thin, 90); z1r = (9/10, 1) nu; penpos2(thick, 180); z2r = (0, 1/2) nu; penpos3(med, 270); z3r = (3/4, 0) nu; penpos4(med, 0); z4r = (3/2, 1/2) nu; penpos5(thin, 90); z5 = (7/10, 14/15) nu; penstroke z1e{left} .. z2e{down} .. z3e .. {up}z4e .. {dir 210}z5e; label(6); endchar; "The numeral 1"; beginchar("1", num_wd, num_ht, 0); penpos1(med, 270); z1 = (0, 1/2) nu; penpos2(med, 0); z2l = z3r; penpos3(thick, 180); z3 = (1, 1) nu; penpos4(thick, 180); z4 = (1, 0) nu; penstroke z1e .. {up}z2e; penstroke z3e .. z4e; penpos5(med, 270); z4 = 1/2[z5r, z6r]; penpos6(med, 270); z6r = (3/2, 0) nu; penstroke z5e .. z6e; label(6); endchar; "The numeral 2"; beginchar("2", num_wd, num_ht, 0); penpos1(thin, 90); z1 = (1/2, 1/2) nu; penpos2(med, 0); z2l = (1/5, 2/3) nu; penpos3(med, 270); x3 = 1/2[x2,x4]; y3l = straight_ascend * ex; penpos4(thick, 180); z4 = (5/4, 2/3) nu; penpos5(med, 90); z5l = (1/3, 0) nu; penpos6(med, 0); z6l = (0, 1/8) nu; penpos7(med, 240); z7 = (3/5, 1/8) nu; penpos8(med, 270); z8r = (1, 0) nu; penpos9(thin, 0); z9r = (3/2, 1/4) nu; penstroke z1e .. z2e .. z3e .. z4e .. tension 1.6 .. z5e{left} .. z6e{up} .. z7e .. z8e{right} .. {up}z9e; label(9); endchar; "The numeral 3"; beginchar("3", num_wd, num_ht, 0); penpos1(thin, 0); z1 = (1/4, 3/4) nu; penpos2(med, 270); z2l = (3/4, 1) nu; penpos3(thick, 180); z3 = (13/10, 3/4) nu; penpos4(med, 90); z4 = (5/8, 1/2) nu; penstroke z1e .. z2e{right} .. z3e .. {left}z4e; penpos5(med, 270); z5 = z4; penpos6(thick, 180); z6l = (3/2, 1/4) nu; penpos7(med, 90); z7l = (3/4, 0) nu; penpos8(thin, 0); z8l = (0, 3/10) nu; penstroke z5e{right} .. z6e .. z7e .. z8e; label(8); endchar; "The numeral 4"; beginchar("4", num_wd, num_ht, 0); penpos1(thick, 180); z1 = (3/4, 1) nu; penpos2(med, 90); z2 = (0, 1/4) nu; penstroke z1e{down} .. z2e; penpos3(med, 270); z3 = z2; penpos4(med, 270); z4 = (3/2, 1/4) nu; penstroke z3e .. z4e; penpos5(thick, 180); z5 = (1, 1/2) nu; penpos6(thick, 180); z6 = (1, 0) nu; penstroke z5e .. z6e; label(6); endchar; "The numeral 5"; beginchar("5", num_wd, num_ht, 0); penpos1(med, 270); z1l = (1/6, 1) nu; penpos2(med, 270); z2l = (4/3, 1) nu; penstroke z1e{dir 340} .. z2e; penpos3(thick, 180); z3r = z1; penpos4(thick, 180); z4r = (1/6, 1/2) nu; penstroke z3e .. z4e; penpos5(med, 270); z5r = z4l; penpos6(thick, 180); z6l = (3/2, 1/4) nu; penpos7(med, 90); z7l = (3/4, 0) nu; penpos8(thin, 0); z8l = (0, 1/4) nu; penstroke z5e .. z6e .. z7e .. z8e; label(8); endchar; "The numeral 6"; beginchar("6", num_wd, num_ht, 0); penpos1(thin, 90); z1r = (5/4, 1) nu; penpos2(thick, 180); z2r = (0, 1/3) nu; penpos3(med, 270); z3r = (3/4, 0) nu; penpos4(med, 0); z4r = (3/2, 1/4) nu; penpos5(med, 180); z5l = z2l; penstroke z1e .. z2e{down} .. z3e .. z4e .. z5e; label(5); endchar; "The numeral 7"; beginchar("7", num_wd, num_ht, 0); penpos1(med, 270); z1l = (0, 1) nu; penpos2(med, 270); z2l = (3/2, 1) nu; penstroke z1e{dir 340} .. z2e; penpos3(thick, 180); z3l = z2r; penpos4(thick, 180); z4r = (1/2, 0) nu; penstroke z3e .. {down}z4e; penpos5(med, 270); penpos6(med, 270); 1/2[z5, z6] = (z3 .. {down}z4) intersectionpoint ((0,1/2) nu .. (3/2,1/2) nu); z6 - z5 = (z2 - z1) / 2; penstroke z5e .. z6e; label(6); endchar; "The numeral 8"; beginchar("8", num_wd, num_ht, 0); penpos1(thin, 90); z1r = (9/10, 1) nu; penpos2(thick, 180); z2 = (1/6, 3/4) nu; penpos3(thick, 210); z3 = 1/2[z2, z4]; penpos4(thick, 180); z4l = (3/2, 1/4) nu; penpos5(med, 90); z5l = (3/4, 0)nu; penpos6(med, 0); z6l = (0, 1/4) nu; penpos7(med, 330); z7 = 1/2[z6, z8]; penpos8(med, 0); z8 = (4/3, 3/4) nu; penpos9(thin, 90); z9r = (6/10, 19/20) nu; penstroke z1e{left} .. z2e .. z3e .. z4e .. z5e .. z6e .. z7e .. z8e .. z9e; label(9); endchar; "The numeral 9"; beginchar("9", num_wd, num_ht, 0); penpos1(med, 90); z1r = (3/2, 9/10) nu; penpos2(med, 90); z2r = (7/8, 1) nu; penpos3(thick, 180); z3r = (1/6, 3/4) nu; penpos4(med, 0); z4r = (3/2, 2/3) nu; penstroke z1e .. z2e .. z3e .. z4e; penpos5(thick, 180); z5l = (3/2, 19/20) nu; penpos6(thick, 180); z6l = (3/2, 1/3) nu; penpos7(med, 90); z7l = (3/4, 0) nu; penpos8(thin, 0); z8l = (0, 1/4) nu; penstroke z5e .. z6e{down} .. z7e{left} .. z8e; label(8); endchar; %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %%\sec Punctuation marks. %{{{1 %% In order to put inter-letter links at the right positions, we had to remove %% any spacing onthe right of letters. For this reason, we add a spacing, %% proportional to the links' widths, at the left of all punctuatin marks. "Exclamation mark"; beginchar("!", ltr_wd(1/2,2), loop_ascend * ex#, 0); penpos1(thick, 180); z1 = ((base_width + 2 link_width) / 2, loop_ascend) * ex; penpos2(med, 180); z2 = (x1, 3/5 ex); penstroke z1e .. z2e; pickup pencircle scaled dot_size; bot z3 = (x1, 0); drawdot z3; label(3); save_letter(exclam)(x1) endchar; "Spanish opening exclamation"; beginchar(189, ltr_wd(1/2,2), (loop_ascend - straight_descend) * ex#, straight_descend * ex#); addto currentpicture also letter.exclam scaled -1 shifted ((1/2 base_width + 2 link_width, loop_ascend - straight_descend) * ex) endchar; "Apostrophe"; beginchar("'", ltr_wd(1/3,2), straight_ascend * ex#, 0); penpos1(thick, 180); z1 = ((base_width + 3 link_width) / 3, straight_ascend) * ex; penpos2(thin, 90); z2 = ((base_width - 3 link_width) / 3, straight_ascend - 1/2) * ex; penstroke z1e{down} .. z2e; label(2); endchar; "High apostrophe"; beginchar(18, ltr_wd(1/3,2), loop_ascend * ex#, 0); penpos1(thick, 180); z1 = ((base_width + 3 link_width) / 3, loop_ascend) * ex; penpos2(thin, 90); z2 = ((base_width - 3 link_width) / 3, loop_ascend - 1/2) * ex; penstroke z1e{down} .. z2e; label(2); endchar; "Reverse apostrophe"; beginchar("`", ltr_wd(1/3,2), straight_ascend * ex#, 0); penpos1(thick, 180); z1 = ((base_width - 3 link_width) / 3, straight_ascend) * ex; penpos2(thin, 270); z2 = ((base_width + 3 link_width) / 3, straight_ascend - 1/2) * ex; penstroke z1e{down} .. z2e; label(2); endchar; "Comma"; beginchar(",", ltr_wd(1/3,2), ex#, 1/3 ex#); penpos1(thick, 180); z1 = ((base_width + 3 link_width) / 3, 1/4) * ex; penpos2(thin, 90); z2l = ((base_width - 3 link_width) / 3, -1/3) * ex; penstroke z1e{down} .. z2e; label(2); endchar; "Hyphen"; beginchar("-", ltr_wd(5/6,0), ex#, 0); penpos1(thick, 260); z1 = (1/6, 1/2) u; penpos2(thick, 260); z2 = (4/6, 1/2) u; penstroke z1e .. z2e; label(2); endchar; "En dash"; beginchar(21, ltr_wd(1,0), ex#, 0); penpos1(med, 270); z1 = (0, 1/2) u; penpos2(med, 270); z2 = (1, 1/2) u; penstroke z1e .. z2e; label(2); endchar; "Em dash"; beginchar(22, ltr_wd(2,0), ex#, 0); penpos1(med, 270); z1 = (0, 1/2) u; penpos2(med, 270); z2 = (2, 1/2) u; penstroke z1e .. z2e; label(2); endchar; "Period"; beginchar(".", ltr_wd(1/2,2), ex#, 0); pickup pencircle scaled dot_size; bot z1 = ((base_width + 2 link_width) / 2 * ex, 0); drawdot z1; label(1) endchar; "Colon"; beginchar(":", ltr_wd(1/2,2), ex#, 0); pickup pencircle scaled dot_size; bot z1 = ((base_width + 2 link_width) / 2 * ex, 0); drawdot z1; top z2 = ((base_width + 2 link_width) / 2 * ex, ex); drawdot z2; label(2) endchar; "Semicolon"; beginchar(";", ltr_wd(1/3,2), ex#, 1/3 ex#); penpos1(thick, 180); z1 = ((base_width + 3 link_width) / 3, 1/4) * ex; penpos2(thin, 90); z2l = ((base_width - 3 link_width) / 3, -1/3) * ex; penstroke z1e{down} .. z2e; pickup pencircle scaled dot_size; top z3 = ((base_width + 3 link_width) / 3 * ex, ex); drawdot z3; label(3); endchar; "Question mark"; beginchar("?", ltr_wd(3/2,2), loop_ascend * ex#, 0); penpos1(med, 90); z1 = z2 - (2/4, 4/5) u; penpos2(med, 270); x2 = x4; y2l = loop_ascend * ex; penpos3(thick, 180); z3l = z1 + (5/4, 1/5) u; penpos4(med, 180); z4 = (3/5 base_width + 3 link_width, 5/6) * ex; penpos5(thin, 180); z5 = z4 - (0, 1/3) u; penstroke z1e .. z2e{right} .. z3e .. z4e .. z5e; pickup pencircle scaled dot_size; bot z6 = (x4, 0); drawdot z6; label(6); save_letter(interg)(x2) endchar; "Spanish opening interrogation"; beginchar(190, ltr_wd(3/2,2), (loop_ascend - straight_descend) * ex#, straight_descend * ex#); addto currentpicture also letter.interg scaled -1 shifted ((3/2 base_width + 2 link_width, loop_ascend - straight_descend) * ex); endchar; "Left parenthesis"; beginchar("(", ltr_wd(1,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(med, 180); z1l = (5/6, loop_ascend) u; penpos2(thick, 180); x2r = 1/6 v; y2 = 1/2[y1,y3]; penpos3(med, 180); z3l = (5/6, -1/2 loop_descend) u; penstroke z1e .. z2e .. z3e; label(3); endchar; "Right parenthesis"; beginchar(")", ltr_wd(1,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(med, 180); z1r = (1/6, loop_ascend) u; penpos2(thick, 180); x2l = 5/6 v; y2 = 1/2[y1,y3]; penpos3(med, 180); z3r = (1/6, -1/2 loop_descend) u; penstroke z1e .. z2e .. z3e; label(3); endchar; "Left bracket"; beginchar("[", ltr_wd(1,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(med, 90); z1r = (5/6, loop_ascend) u; penpos2(med, 90); z2r = (1/6, loop_ascend) u; penpos3(thick, 180); z3r = (1/6, loop_ascend) u; penpos4(thick, 180); z4r = (1/6, -1/2 loop_descend) u; penpos5(med, 270); z5r = (1/6, -1/2 loop_descend) u; penpos6(med, 270); z6r = (5/6, -1/2 loop_descend) u; if fixed: draw z1 -- z2 -- z5 -- z6 withpen pencircle scaled med; else: penstroke z1e .. z2e; penstroke z3e .. z4e; penstroke z5e .. z6e; fi label(6); endchar; "Right bracket"; beginchar("]", ltr_wd(1,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(med, 270); z1l = (1/6, loop_ascend) u; penpos2(med, 270); z2l = (5/6, loop_ascend) u; penpos3(thick, 180); z3l = (5/6, loop_ascend) u; penpos4(thick, 180); z4l = (5/6, -1/2 loop_descend) u; penpos5(med, 90); z5l = (5/6, -1/2 loop_descend) u; penpos6(med, 90); z6l = (1/6, -1/2 loop_descend) u; if fixed: draw z1 -- z2 -- z5 -- z6 withpen pencircle scaled med; else: penstroke z1e .. z2e; penstroke z3e .. z4e; penstroke z5e .. z6e; fi label(6); endchar; "Left brace"; beginchar("{", ltr_wd(7/6,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(med, 90); penpos2(thick, 180); penpos3(med, 90); penpos4(med, 270); penpos5(thick, 180); penpos6(med, 270); x1 = x6 = v; y1r = loop_ascend * ex; y6r = -1/2 loop_descend * ex; z3 = z4 = (1/6 v, 1/2[y1,y6]); z2 = 1/2 [z1, z3]; z5 = 1/2 [z4, z6]; penstroke z1e {left} .. z2e .. {left} z3e; penstroke z4e {right} .. z5e .. {right} z6e; label(6); endchar; "Right brace"; beginchar("}", ltr_wd(7/6,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(med, 270); penpos2(thick, 180); penpos3(med, 270); penpos4(med, 90); penpos5(thick, 180); penpos6(med, 90); x1 = x6 = 1/6 v; y1l = loop_ascend * ex; y6l = -1/2 loop_descend * ex; z3 = z4 = (v, 1/2[y1,y6]); z2 = 1/2 [z1, z3]; z5 = 1/2 [z4, z6]; penstroke z1e {right} .. z2e .. {right} z3e; penstroke z4e {left} .. z5e .. {left} z6e; label(6); endchar; "Slash"; beginchar("/", ltr_wd(2,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(thick, 180); z1l = (w - 1/6 v, loop_ascend * ex); penpos2(thick, 180); z2r = (1/6 v, -1/2 loop_descend * ex); penstroke z1e .. z2e; label(2); endchar; "Vertical bar"; beginchar("|", ltr_wd(1,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(thick, 180); z1 = (w/2, loop_ascend * ex); penpos2(thick, 180); z2 = (w/2, -1/2 loop_descend * ex); penstroke z1e .. z2e; label(2); endchar; "Reverse slash"; beginchar("\", ltr_wd(2,0), loop_ascend * ex#, 1/2 loop_descend * ex#); penpos1(thick, 180); z1r = (1/6 v, loop_ascend * ex); penpos2(thick, 180); z2l = (w - 1/6 v, -1/2 loop_descend * ex); penstroke z1e .. z2e; label(2); endchar; "Ampersand"; beginchar("&", ltr_wd(3,0), uc_ascend * ex#, 0); penpos1(thick, 180); z1 = (9/4, 1/2) uu; penpos2(med, 90); z2l = (11/16, 0) uu; penpos3(med, 0); z3l = (0, 1/6) uu; penpos5(med, 0); z5 = (8/5, 13/16) uu; penpos4(med, angle(z5-z3)-90); z4 = 1/2[z3,z5]; penpos6(med, 90); z6r = (9/8, 1) uu; penpos7(thick, 180); z7 = (3/4, 1/2) uu; penpos8(med, 270); z8r = (2, 0) uu; penpos9(med, 0); z9r = (3, 1/5) uu; penstroke z1e .. z2e .. z3e{up} .. z4e .. {up}z5e .. z6e .. z7e .. z8e .. z9e; label(9); endchar; "French opening quote"; beginchar(19, ltr_wd(11/10,2), ex#, 0); penpos1(thick, 150); y1r = ex; penpos2(thin, 90); z2 = (link_width, 1/2) u; penpos3(thick, 30); y3l = 0; x1l = x3r = w - (link_width + 2/5) * v; penstroke z1e .. {dir 190} z2e; penstroke z3e .. {dir 170} z2e; label(3); addto currentpicture also currentpicture shifted (2/5 v, 0); endchar; "French closing quote"; beginchar(20, ltr_wd(11/10,2), ex#, 0); penpos1(thick, 210); y1l = ex; penpos2(thin, 270); z2 = (w - (link_width + 2/5) * v, ex/2); penpos3(thick, 330); y3r = 0; x1r = x3l = link_width * v; penstroke z1e .. {dir -10} z2e; penstroke z3e .. {dir 10} z2e; label(3); addto currentpicture also currentpicture shifted (2/5 v, 0); endchar; "Less than sign"; beginchar("<", ltr_wd(3/2,2), num_ht, 0); penpos1(med, 90); z1r = (3/2 + link_width, 9/10 straight_ascend) u; penpos2(med, 90); z2 = (link_width, 1/2 straight_ascend) u; penpos3(med, 90); z3l = (3/2 + link_width, 1/10 straight_ascend) u; penstroke z1e .. z2e; penstroke z3e .. z2e; label(3); endchar; "Greater than sign"; beginchar(">", ltr_wd(3/2,2), num_ht, 0); penpos1(med, 270); z1r = (link_width, 9/10 straight_ascend) u; penpos2(med, 270); z2 = (3/2 + link_width, 1/2 straight_ascend) u; penpos3(med, 270); z3l = (link_width, 1/10 straight_ascend) u; penstroke z1e .. z2e; penstroke z3e .. z2e; label(3); endchar; %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %% %%\sec The ligature table. %{{{1 %% Here comes a crucial part of the French Cursive typeface: the ligature and %% kerning table. It has to play two major roles: first of all, it is %% responsible of the insertion of inter-letter links, a task for which the %% lig/kern system in \TeX\ and \MF\ is thankfully powerful enough. Secondly, %% this table is responsible for kerning, which is necessary for some %% successions of an uppercase and a lowercase, but also in some cases for %% punctuation. %%\subsec Macros for ligature tables. %{{{2 k# := base_width * ex#; "Right boundary pseudo-character"; beginchar(23, 0, 0, 0) endchar; boundarychar := 23; def word_ends = ".", ",", ";", ":", "'", ")", "]", "/", 20, "-", 21, 22 enddef; %% The sets of variants of letters. def var_a = "a",160,161,224,225,226,227,228,229 enddef; def var_c = "c",162,163,231 enddef; def var_d = "d",164 enddef; def var_e = "e",165,166,232,233,234,235 enddef; def var_g = "g",167 enddef; def var_i = "i",236,237,238,239 enddef; def var_l = "l",168,169,170 enddef; def var_n = "n",171,172,241 enddef; def var_o = "o",174,242,243,244,245,246,248 enddef; def var_r = "r",175,176 enddef; def var_s = "s",177,178,179 enddef; def var_t = "t",180,181 enddef; def var_u = "u",182,183,249,250,251,252 enddef; def var_y = "y",184,253 enddef; def var_z = "z",185,186,187 enddef; %% The sets of shapes for links. def sh_small = var_a, var_c, var_d, var_e, var_g, var_o, "q", 247 enddef; def sh_loop = "b", "f", "h", "k", var_l enddef; def sh_vert = var_i, var_r, var_t, var_u, var_z enddef; def sh_far = "j", "p", var_s enddef; def sh_hloop = "h", "k" enddef; def sh_mn = "m", var_n, "v", "w", "x", var_y enddef; def sh_x = "x" enddef; %% Some macros to use these lists. boolean ligged[], first; def ligtables (text list) = ligtable for c = list: if not known ligged[byte c]: hide ( ligged[byte c] = true ) c: fi endfor enddef; def link (text list) (expr chr) = hide(first := true) for lft = list: if first: hide(first := false) else: , fi lft |=:| chr endfor enddef; def links (suffix ln) (text sh) = hide (first := true) forsuffixes # = sh: if first: hide(first := false) else: , fi expandafter link expandafter ( scantokens ("sh_" & str #) )(lnk.#.ln) endfor enddef; %%% ligtable ligtables %%% penpos link links %%\subsec Ligatures between lowercase and punctuations. %{{{2 ligtable "-": "-" =: 21, skipto 0; ligtable 21: "-" =: 22, skipto 0; ligtable "!": "`" =: 189; ligtable "?": "`" =: 190; ligtable "`": "`" kern -2 link_width * k#, skipto 0; ligtable "'": "'" kern -2 link_width * k#, skipto 0; ligtable 18: "'" =:| "'", skipto 0; ligtable "<": "<" =: 19; ligtable ">": ">" =: 20; ligtable ||: "(": ")": "[": "]": "{": "}": "/": "|": "\": 189: 190: ".": ":": ";": 20: 22: 0:: link(sh_far)(lnk.far.low), link(sh_mn)(lnk.mn.beg), skipto 2; %%\subsec Ligatures between lowercase letters. %{{{2 %% Special cases: the q and the s have a different shape at the end of words, %% they have no right link, contrary to the other letters. ligtables ("q", var_s) for c = 97 upto 122: c |=:| lnk.sq, endfor for c = 160, 161, 162, 163, 165, 166, 167, 168, 170, 171, 172, 175, 176, 177, 178, 179, 181, 183, 185, 186, 187: c |=:| lnk.sq, endfor for c = 224 upto 252: if (c <> 230) and (c <> 240): c |=:| lnk.sq, fi endfor 253 |=:| lnk.sq; ligtables ("h", "k") "'" |=: 18, skipto 1; ligtables (var_a, var_d, var_i, "m", var_n, "p", var_r, var_u, lnk.sq) 1:: for lt = boundarychar, word_ends: lt |=:| lnk.lowmed, endfor skipto 2; ligtables (lnk.low) 2:: links (low) (small, hloop, loop, vert, far, mn, x); ligtables (var_l) "'" |=: 18, skipto 3; ligtables (var_c, var_e, "f", var_g, "j", var_t, "x", var_y, var_z, 247) 3:: links (med) (small, hloop, loop, vert, far, mn, x); ligtables (lnk.high) for c = var_e: c kern -thin#, endfor skipto 5; ligtables ("b") "'" |=: 18, skipto 4; ligtables (var_o, "v", "w") 4:: for c = var_e: c |=:| lnk.high, endfor for c = "-", 21, 22: c kern thin#, endfor 5:: links (high) (small, loop, vert, far, mn); %%\subsec Ligatures and spacings after uppercase letters. %{{{2 ligtable "G": "J": "Y": 221: links (med) (small, hloop, loop, vert, far, mn, x); ligtable "F": "S": lnk.small.low kern -1/2 k#, % small letters are closer lnk.vert.low kern -1/4 k#, % verticals too lnk.far.med kern -1/5 k#, % j, p, s too link(sh_small)(lnk.small.low), skipto 6; ligtable "I": 204: 205: 206: 207: for l = lnk.loop.high, lnk.vert.low, lnk.mn.beg: l kern 1/8ex#, endfor skipto 6; ligtable "N": 209: lnk.small.low kern -1/3 k#, lnk.far.med kern -1/5 k#, skipto 6; ligtable "P": lnk.small.low kern -5/8 k#, lnk.far.med kern -1/3 k#, lnk.vert.low kern -5/12 k#, skipto 6; ligtable "Q": lnk.mn.beg kern 1/5 k#, link(sh_small)(lnk.small.low), skipto 6; ligtable "H": "K": "L": lnk.small.low kern 1/8 k#, lnk.mn.beg kern 1/6 k#, skipto 6; ligtable "B": "C": 199: "D": "M": "R": "T": "V": "W": "X": "Z": "A": 192: 193: 194: 195: 196: 197: "E": 200: 201: 202: 203: "O": 210: 211: 212: 213: 214: 216: "U": 217: 218: 219: 220: lnk.mn.beg kern 1/6 k#, 6:: links (med) (hloop), links (low) (small, loop, vert), links (med) (far), links (beg) (mn); bye.