%D \module
%D   [       file=m-graph,
%D        version=2000.08.06,
%D          title=\CONTEXT\ Extra Modules,
%D       subtitle=\METAPOST\ graph module support,
%D         author=Hans Hagen,
%D           date=\currentdate,
%D      copyright={PRAGMA / Hans Hagen \& Ton Otten}]
%C
%C This module is part of the \CONTEXT\ macro||package and is
%C therefore copyrighted by \PRAGMA. See mreadme.pdf for 
%C details. 

%D I finally finished graph support, if only because I could 
%D not stand the idea that Karel Wesseling would revert to 
%D \PiCTeX. 

% pre 2000.08.06 version  
%
% \forceMPTEXgraphictrue 
% 
% \appendtoks 
%   initialize_numbers ; % make sure that pseudo typesetting is set up
%   input graph ;        % load the graph package 
%   Autoform := "@g" ;   % change the % template char into @ 
% \to \MPinitializations 

%D The latest version does things more automatically (and 
%D efficiently when no text processing is needed). For 
%D definitions embedded in your document, you need to 
%D use \type {@} as template character, in external files, 
%D \type {%} is also supported. 

\appendtoks input graph ; \to \MPinitializations 

%D Graphics that have \type {begingraph} in them are 
%D recognized as such and force handling of embedded \TEX\ 
%D code. 

\forceMPTEXcheck{begingraph}
   
%D If you run into troubles, try: 
%D 
%D \starttypen 
%D \forceMPTEXgraphictrue 
%D \stoptypen 
%D
%D A demo can be run with:
%D
%D \starttypen
%D texexec --mode=demo --pdf m-graph
%D \stoptypen 

% No longer needed, since John will fix it. 
% 
% %D For the moment we need the following patch. Adam T. Lindsay 
% %D found out that the following code produced an error: 
% %D 
% %D \starttypen 
% %D \startMPcode
% %D draw begingraph(130mm,35mm);
% %D   setrange(0,0,10,22000);
% %D   glabel.lft(btex  {correct 0--22000} etex rotated 90, OUT);
% %D   autogrid(itick.bot,grid.lft) withcolor .75white ;
% %D   endgraph;
% %D \stopMPcode
% %D 
% %D \startMPcode
% %D draw begingraph(130mm,35mm);
% %D   setrange(0,50,10,22000);
% %D   glabel.lft(btex  {wrong 50--22000} etex rotated 90, OUT);
% %D    autogrid(itick.bot,grid.lft) withcolor .75white ;
% %D   endgraph;
% %D \stopMPcode
% %D 
% %D \startMPcode
% %D draw begingraph(130mm,35mm);
% %D   setrange(0,110,10,30000);
% %D   glabel.lft(btex  {failed 110--22000} etex rotated 90, OUT);
% %D    autogrid(itick.bot,grid.lft) withcolor .75white ;
% %D   endgraph;
% %D \stopMPcode
% %D \stoptypen 
% %D
% %D The bug is a rather nasty one and needs some tweaking in 
% %D the low level graph code. John Hobby suggested for the 
% %D moment to initialize \type {setrange} as follows: 
% %D 
% %D \starttypen  
% %D  setrange(0,0,"22000","22000")
% %D \stoptypen 
% %D 
% %D Folowing this suggesion, I provide the following 
% %D extension: 
% 
% % \appendtoks 
% def begingraph(expr w, h) =
%   begingroup
%   save X_, Y_, Gfin_, Gcur_, Gcbb_, Gneedgr_, Gneedfr_, Gdidsc_;
%   save Gdpic_, Gppic_, Ggl_, Garw_;
%   picture Gfin_, Gcur_, Gcbb_, Gdpic_, Gppic_, Ggl_[];
%   boolean Gneedgr_, Gneedfr_, Gdidsc_;
%   Gfin_ = nullpicture;          
%   Gcur_ = nullpicture;          
%   Gcbb_ = nullpicture;          
%   X_.ctyp = Y_.ctyp = linear;   
%   Z_.gdim = (w,h);              
%   X_.sc = Y_.sc = 0;            
%   Gneedgr_ = true;              
%   Gneedfr_ = true;              
%   Gdidsc_ = false;              
%   Gdpic_ = nullpicture;         
%   Garw_ = 0;                    
%   scantokens everybegingraph ; 
% enddef;
% 
% boolean fixsetrange ; fixsetrange := true ; 
% 
% vardef dosetrange(text t) =
%   interim warningcheck:=0;
%   save r_; r_=0;
%   string r_[]s;
%   for x_=
%       for p_=t: if pair p_: xpart p_, ypart fi p_, endfor:
%     r_[incr r_] if string x_: s fi = x_;
%     if r_>2:
%       Gsetr_ if r_=3: X_(Gxcvlin_) else: Y_(Gycvlin_) fi(
%           r_[r_-2] if unknown r_[r_-2]: s fi, x_);
%     fi
%     exitif r_=4;
%   endfor
% enddef;
% 
% vardef setrange(text t) =
%   if fixsetrange : dosetrange(0,0,20000,20000) ; fi ; 
%   dosetrange(t) ;
% enddef ; 
% 
% if unknown everybegingraph : 
%   string everybegingraph ;
% % everybegingraph := "setrange(0,0,20000,20000)" ; 
% fi ; 
% \to \MPinitializations 

\appendtoks 
  % @# is X_ or Y_; $ is Gxcvlin_ or Gycvlin_; l and h are numeric or string
  % It would not be OK to set (@#low,@#high) to a pair expression because $ might
  % try to rescale @#low when evaluating the right-hand side for @#high.
  vardef Gsetr_@\#(suffix $)(expr l, h) =
    Gclbnds_@\# ;
    if @\#ctyp>0 :
       @\#low  = if abs @\#ctyp<>log: $ fi Mlog_Str l ;
       @\#high = if abs @\#ctyp<>log: $ fi Mlog_Str h ;
    else :
      -@\#high = if abs @\#ctyp<>log: $ fi Mlog_Str l ;
      -@\#low  = if abs @\#ctyp<>log: $ fi Mlog_Str h ;
    fi
  enddef ;
\to \MPinitializations 

\doifnotmode {demo} {\endinput} 

%D You need to have the data files in your path, 
%D otherwise the run is aborted.

\doiffileelse {agepop91.d}
  {} {\writestatus{graph}{no data files found}\wait\end}

%D The test: 

\starttext 

\startMPpage
draw begingraph(3in,2in);
  gdraw "agepop91.d";
  endgraph;
\stopMPpage

\startMPpage
draw begingraph(3in,2in);
  gdraw "agepop91.d" plot btex$\bullet$etex;
  endgraph;
\stopMPpage

\startMPpage
draw begingraph(3in,2in);
  glabel.lft(btex \vbox{\hbox{Population} \hbox{in millions}} etex, OUT);
  glabel.bot(btex Age in years etex, OUT);
  gdraw "agepopm.d";
  endgraph;
\stopMPpage

\startMPpage
draw begingraph(3in,2in);
 glabel.lft(btex \vbox{\hbox{Population} \hbox{in millions}} etex, OUT);
 glabel.bot(btex Age in years etex, OUT);
 setrange(origin, whatever,whatever);
 gdraw "agepopm.d";
 endgraph;
\stopMPpage

\startMPpage
draw begingraph(2.3in,2in);
 setcoords(log,log);
 glabel.lft(btex Seconds etex,OUT);
 glabel.bot(btex Matrix size etex,
   OUT);
 gdraw "matmul.d" dashed evenly;
 glabel.ulft(btex Standard etex,8);
 gdraw "matmul.d";
 glabel.lrt(btex Strassen etex,7);
 endgraph;
\stopMPpage

\startMPpage
draw begingraph(6.5cm,4.5cm);
 setrange(80,0, 90,whatever);
 glabel.bot(btex Year etex, OUT);
 glabel.lft(btex \vbox{\hbox{Emissions in} \hbox{thousands of}
   \hbox{metric tons} \hbox{(heavy line)}}etex, OUT);
 gdraw "lead.d" withpen pencircle scaled 1.5pt;
 autogrid(,otick.lft);
 setcoords(linear,linear);
 setrange(80,0, 90,whatever);
 glabel.rt(btex \vbox{\hbox{Micrograms} \hbox{per cubic}
   \hbox{meter of air} \hbox{(thin line)}}etex, OUT);
 gdraw "lead.d";
 autogrid(otick.bot,otick.rt);
 endgraph;
\stopMPpage

\stoptext
