%%% @mffile{
%%%     filename="mftools.mf",
%%%     version="",
%%%     date="",
%%%     filetype="mf inputfile",
%%%     package="m-capbas.arj"
%%%     author="Phons Bloemen (PhB)",
%%%     address="Eindhoven U. of Technology,
%%%            Fac. of Electrical Engineering,
%%%            P. O. Box 513, NL-5600 MB Eindhoven
%%%     email="Internet: phons@ei.ele.tue.nl",
%%%     codetable="ISO/ASCII",
%%%     checksumtype="none",
%%%     checksum="0",
%%%     keywords="",
%%%     abstract="Metafont file containing a collection of
%%%        macros to do various funny things to characters.
%%%        Usage: copy a standard font file ('cmtt10.mf') and
%%%        paste a copy of the 'endchar' function from 'plain.mf'
%%%        into it. Edit the 'endchar' function to your wishes
%%%        using these macros. The macros work on the already
%%%        rendered characters before they are stored into the
%%%        font. Let METAFONT run and watch the results!
%%%        Examples of changed 'endchars' in cmbugs.mf and cmgray.mf
%%%        Part of Capital Baseball package"
%%%     copyright="Copyleft (L) Phons Bloemen (PhB),
%%%        according to GNU public licence version 2 or later.
%%%        (1) Do not change this file (even its name)
%%%        (2) if you do make changes, first rename it to some
%%%            other name, and mark your changes clearly.",
%%%     }
%%
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% To 'outline' a picture. Only the 'edge' of a picture remains.
% Thickness of edge controlled by 'th'.
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
def ooutline (expr th) =
   save v,n;
   cull currentpicture keeping (1,infinity);
   picture v; v:= currentpicture;
   clearit;
   for n = 0 step 45 until 359:
       addto currentpicture also (v shifted ((0,th) rotated n));
       addto currentpicture also -v;
       cull currentpicture keeping (-infinity,-1) withweight -1;
   endfor;
   cull currentpicture keeping (-infinity,-1);
enddef;

def outline (expr th) =
   begingroup;
   save v,n;
   cull currentpicture keeping (1,infinity);
   picture v; v:= currentpicture;
   clearit;
   for n = 0 step 24 until 359:
       addto currentpicture also (v shifted ((0,th) rotated n));
   endfor;
   cull currentpicture keeping (1,infinity);
   addto currentpicture also -v;
   endgroup;
enddef;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% To 'double outline' a picture, with a surrounding line.
% Parameter tha controls the thickness of the surrounding line,
% parameter thb-tha controls the distance between line and picture
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
def douboutline (expr thb,tha) =
   begingroup;
   save va,vb;
   picture va,vb; va:=currentpicture;
   outline(tha);
   vb := currentpicture;
   currentpicture := va;
   outline(thb);
   addto currentpicture also va - vb;
   cull currentpicture keeping (1,infinity);
   endgroup;
enddef;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% gentile: generate a tiling pattern
% A pattern of tiles is generated, large enough to cover any
% character in the font. One tile is k*l 'units' long. The units
% are numbered 0 -- (k*l)-1. On the units listed in 't', a dot is
% put down with the pencil typed by 'potlood'. The parameters
% 'ww,hh,dd' outline the largest character in the font.
% Use the gentile macro before doing anything with the font, and
% save the resulting tiling pattern in a separate 'picture'
% variable. This picture variable can then be used by 'tilepic'.
% Parameters:
%   ww: base width of the font (width of letter 'M')
%   hh: base height of font (height of capitals)
%   dd: base depth of font (depth of descenders)
%   k, l: the tile consists of k x l 'pixels'
%   gr: granularity factor. The 'currentpicture' is divided into
%       1/gr x 1/gr pixels, the pixels are grouped together to tiles.
%       A pixels will be of size (w*gr * (h+d)*gr). Low values
%       mean finer patterns, but they consume a lot of Metafonts
%       resources, and may be subject to 'discretization'
%       problems. A big metafont can handle about gr=0.001.
%   potlood: A pencil type. Usually a circular tip.
%   t: a list of numbers, indicating        0,1,2
%      the dots in a tile. A 3 x 3          3,4,5
%      tile is numbered like this:          6,7,8
%      Other tile sizes have similar numberings.
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
def gentile(expr gr,k,l,ww,hh,dd,potlood,pict)(text t) =
begingroup
   mode_setup;
   charcode:=0;
   charwd:=ww;
   w:=hround(charwd*hppp);
   charht:=hh;
   h:=vround(charht*hppp);
   chardp:=dd;
   d:=vround(chardp*hppp);
   charic:=0; clearxy; clearit; clearpen; scantokens extra_beginchar;
   pickup potlood xscaled (gr*w/1) yscaled(gr*(h+d)/1);
   for c = t :
      drawdot((c mod k)*gr*w,floor(c/k)*gr*(h+d)-d);
      cull currentpicture keeping (1,infinity) withweight 1;
   endfor;
   for a=1,2,4,8,16,32,64,128,256,512,1024,2048:
      exitif ((a * gr * l) > 1);
      b := (a*gr*l*(h+d));
      addto currentpicture also currentpicture shifted (0,b);
      cull currentpicture keeping (1,infinity) withweight 1;
   endfor;
   for a=1,2,4,8,16,32,64,128,256,512,1024,2048:
      exitif ((a * gr * k) > 1);
      b := (a*gr*k*w);
      addto currentpicture also currentpicture shifted (b,0);
      cull currentpicture keeping (1,infinity) withweight 1;
   endfor;
   groundpattern := currentpicture;
   scantokens extra_endchar;
   chardx:=w;     % desired width of the character in pixels
   pixels_per_inch:=pixels_per_inch/mag;
                  %%% otherwise magnification is squared
endgroup;
enddef;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% The current picture is overlaid by a tiling pattern 'til'. The
% pattern may be generated with 'gentile'
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
def tilepic (expr til) =
   cull currentpicture keeping (1,infinity) withweight 1;
   addto currentpicture also til shifted (0,-d);
   cull currentpicture keeping (2,infinity) withweight 1;
enddef;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% As tilepic, but the current picture is first 'outlined': it
% will become patterned with tile pattern 'til', and with black
% edges. The parameter 'th' controls edge thickness
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
def otilepic (expr til,th)=
   save v,n;
   cull currentpicture keeping (1,infinity);
   picture v; v:= currentpicture;
   clearit;
   for n = 0 step 24 until 359:
       addto currentpicture also (v shifted ((0,th) rotated n));
   endfor;
   cull currentpicture keeping (1,infinity);
   cull v keeping (1,infinity) withweight -1;
   addto v also currentpicture;
   addto currentpicture also til shifted (0,-d);
   cull currentpicture keeping (2,2);
   addto currentpicture also v;
   cull currentpicture keeping (1,infinity);
enddef;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% xmirror and ymirror
% Mirrors a picture. This is done around the central vertical
% (horizontal) axis of the character: the line x=.5w (y=.5h)
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
def xmirror =
   save v,n,t;
   t := tracingequations;
   tracingequations := 1;
   cull currentpicture keeping (1,infinity);
   picture v; v:= currentpicture;
   clearit;
   currentpicture := v reflectedabout ((0,0), (0,h))
                  shifted (w,0);
enddef;

def ymirror =
   save v,n,t;
   t := tracingequations;
   tracingequations := 1;
   cull currentpicture keeping (1,infinity);
   picture v; v:= currentpicture;
   clearit;
   currentpicture := v reflectedabout ((0,0), (w,0))
                  shifted (0,h);
enddef;

%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
% reversevideo
% Inverts a picture. The outer boundary is assumed to be
% rectangular. A box of width w (character width) and
% height h + d. Here w,h,d are defined by 'beginchar'
%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%%
def reversevideo =
   begingroup;
   save vv,v; picture v,vv;
   cull currentpicture keeping (1,infinity);
   v:= currentpicture;
   clearit;
   fill (0,h)--(w,h)--(w,-d)--(0,-d)--cycle;
   cull currentpicture keeping (1,infinity);
   vv:=currentpicture-v;
   currentpicture:=vv;
   endgroup;
enddef;
