[comp.lang.postscript] PS examples: toy sales graphs

reid@decwrl.dec.com (Brian Reid) (01/29/88)

Here's a file that prints a bunch of fake graphs of sales against time. I put
this together originally as part of an argument with somebody over whether
GKS or PostScript had a more compact representation. I took his GKS file and
recoded it (by hand, admittedly) in PostScript. Mine was about a factor of 8
smaller).

%!
% GKS example with some little PostScript-only games played.
% Brian Reid, 13 June 1985.
/vsc 10.0 def		% vertical scale is 0.1 (horiz is ok)
/llbl [(Jan)(Feb)(Mar)(Apr)(May)(Jun)(Jul)(Aug)(Sep)(Oct)(Nov)(Dec)]def
/stxt /Courier findfont .35 scalefont def
/ntxt /Helvetica findfont .30 scalefont def
/axlbl /Helvetica findfont .46 scalefont def
/ltxt /Times-Roman findfont .6 scalefont def
/GKD 50 dict def /xdf {exch def} def

/markx [1. 2. 3. 4. 5. 6. 7. 8. 9.]def
/marky [.37 .5 .32 .8 .6 .7 .6 .3 .5]def
/bars [.1 .4 .29 .2 .55 .6 .4 .2 .34]def
%---------------------

% (str) x y cshow
/cshow{GKD begin /ctry xdf /ctrx xdf /cstr xdf
       cstr stringwidth pop 2 div ctrx exch sub ctry moveto cstr show end}def

% draw a big dot at current position
/drawdot{gsave currentpoint newpath moveto currentpoint lineto
	lwid 2 mul setlinewidth stroke grestore}def

% xarray yarray /pointfunc linewidth polyline
/polyline{GKD begin gsave 1 setlinecap 1 setlinejoin
	/lwid xdf /ptfunc exch load def /my xdf /mx xdf
	newpath 0 1 my length 1 sub {/i xdf 
	mx i get my i get i 0 eq 
	{moveto}{lineto}ifelse ptfunc} for lwid setlinewidth stroke
	grestore end}def

% llx lly urx ury lwid filltype fbox 
/fbox{GKD begin /tfill xdf
   /lw2 xdf /ury xdf /urx xdf
   /lly exch lw2 add def /llx xdf
   newpath llx lly moveto llx ury lineto urx ury lineto urx lly lineto
   closepath gsave clip gsave tfill setgray fill grestore
   lw2 2 mul setlinewidth stroke
   grestore end
}def

%---------
/maxrand 2 31 exp 1 sub def
/onegraph {
    0 1 8 {/ix exch def marky ix
        rand maxrand div .7 mul dup /vval exch def put
	bars ix rand maxrand div .6 mul .7 add vval mul 
	   dup .8 gt {pop .8} if put
    } for
    gsave 30 30 scale 
    4 7 translate		
    -1.2 -1.2 10.5 10.5 0 0.975 fbox
    ltxt setfont		
    2.2 8.7 7.8 9.7 0 0 fbox 1 setgray
    (Sales of #00000) dup 10 rand maxrand div 89999 mul cvi 10000 add
    (     ) cvs putinterval
    5 9 cshow 0 setgray
    % draw axes 
    newpath 0 9.5 moveto 0 0 lineto 10 0 lineto .05 setlinewidth stroke
    % put Y axis tickmarks
    .025 setlinewidth stxt setfont
    gsave newpath 10{-.17 0 moveto 0 0 lineto 0 1 translate}repeat
	    stroke grestore
    % put X axis tickmarks
    1 1 9 {dup llbl exch 1 sub get exch -0.3 cshow} for
    
    % put X axis label
    axlbl setfont (Calendar Month) 5 -1 cshow
    % put Y axis label
    gsave 90 rotate (Units Sold (thousands)) 4.5 .7 cshow
    stxt setfont 0 1 9 {dup ( ) cvs exch 0.25 cshow}for
    grestore
    
    % draw the boxes
    0 1 8{/i xdf i .65 add 0 i 1.35 add bars i get
	 vsc mul .02 .76 fbox}for

    % draw the X's and connect them with a "polyline"
    markx [ marky {vsc mul}forall ] /drawdot .1 polyline
    
    % put a label along the graph
    gsave markx 0 get marky 0 get vsc mul translate
	  marky 1 get marky 0 get sub vsc mul markx 1 get markx 0 get sub
	  atan rotate .1 0.18 moveto ntxt setfont
	  (Predicted) show grestore
    grestore
    showpage
} def
10 {onegraph} repeat