%% %% This is file `expressg.mp', %% generated with the docstrip utility. %% %% The original source files were: %% %% expressg.dtx (with options: `up') %% %% Author: Peter Wilson (CUA) now at peter.r.wilson@boeing.com until June 2004 %% (or pandgwilson@earthlink.net) %% Copyright 1996, 2003 Peter R. Wilson %% %% v1.0 1996/05/09 (first release) %% v1.2 1999/11/15 %% v1.3 2000/05/22 %% v1.4 2000/07/10 %% v1.5 2003/07/31 %% v1.6 2004/02/29 %% v1.61 2004/03/17 %% %% This work may be distributed and/or modified under the %% conditions of the LaTeX Project Public License, either %% version 1.3 of this license or (at your option) any %% later version. %% The latest version of the license is in %% http://www.latex-project.org/lppl.txt %% and version 1.3 or later is part of all distributions of %% LaTeX version 2003/06/01 or later. %% %% This work has the LPPL maintenance status "author-maintained". %% %% This work consists of the files listed in the README file. %% This program is provided under the terms of the %% LaTeX Project Public License distributed from CTAN %% archives in directory macros/latex/base/lppl.txt. %% %%% EXPRESSG.MP MetaPost macros for EXPRESS-G and other BLA diagrams %%% version 1.5, 31 July 2003 %%% version 1.6, 29 February 2004 %%% version 1.61, 17 March 2004 show "expressg.mp version 1.61, 2004/03/17"; newinternal u; numeric u; u := 1mm; newinternal maxx, maxy; numeric maxx, maxy; maxx := 159.5u; % smidgeon under 160mm for ISO maxy := 210u; % 210mm for ISO newinternal defaultdotdiam, dotdiam; numeric defaultdotdiam, dotdiam; defaultdotdiam := 2u; dotdiam := defaultdotdiam; newinternal normalpensize, thickpensize, thinpensize; numeric normalpensize, thickpensize, thinpensize; normalpensize := 0.5bp; thickpensize := 1.5bp; thinpensize := 0.25bp; newinternal dotsscale; numeric dotsscale; dotsscale := 2; newinternal normalpen, thickpen, thinpen, dotspen, dotpen; pen normalpen, thickpen, thinpen, dotspen, dotpen; normalpen := pencircle scaled normalpensize; % i.e. defaultpen; thickpen := pencircle scaled thickpensize; thinpen := pencircle scaled thinpensize; dotspen := pencircle scaled (dotsscale*normalpensize); dotpen := pencircle scaled dotdiam; newinternal defaultsmoothrad; numeric smoothrad, defaultsmoothrad; smoothrad := defaultsmoothrad := 2u; newinternal defaultdrumlid; numeric drumlid, defaultdrumlid; drumlid := defaultdrumlid := 0.2; %%% default length and base width for arrowheads and fanin newinternal defaultgal, defaultgab, defaultgfl, defaultgfb; numeric defaultgal, defaultgab, defaultgfl, defaultgfb; defaultgal := defaultgfl := defaultdotdiam; defaultgab := defaultgfb := defaultgal; %%% length and base width of arrowheads and fanins newinternal gal, gab, gfl, gfb; numeric gal, gab, gfl, gfb; gal := defaultgal; gab := defaultgab; gfl := defaultgfl; gfb := defaultgfb; newinternal onelineh; numeric onelineh; onelineh := 5u; %%% length, height & inset for simple data type boxes newinternal sdtbl, sdtbh, sdtbs; numeric sdtbl, sdtbh, sdtbs; sdtbl := 22u; sdtbh := onelineh; sdtbs := 2u; %%% length, height & inset for EXPRESSION data type boxes newinternal sdtbel, sdtbeh, sdtbes; numeric sdtbel, sdtbeh, sdtbes; sdtbel := 28u; sdtbeh := sdtbh; sdtbes := sdtbs; %%% length, height & inset for GENERICENT data type boxes newinternal sdtbgel, sdtbgeh, sdtbges; numeric sdtbgel, sdtbgeh, sdtbges; sdtbgel := 38u; sdtbgeh := sdtbh; sdtbges := sdtbs; %%% average length of numeric page connector newinternal pconl; numeric pconl; % length of page connector (for e.g., 9,9 (9,9) ) pconl:=15u; %%% height of page connectors (one line) newinternal pconh; numeric pconh; pconh := onelineh; %%% heights of entity, enum, select, type boxes (One text line) newinternal enth, typeh; numeric enth, typeh; enth := onelineh; typeh := onelineh; %%% height of interschema boxes (one text line, no rename), and (name + rename) newinternal ish, isrh; numeric ish, isrh; ish := 2onelineh; isrh := 3onelineh; %%% height of schema boxes (one text line) newinternal schemah; numeric schemah; schemah := 2onelineh; %%% height and slope of event boxes newinternal eventh, eventslope; numeric eventh, eventslope; eventh := onelineh; eventslope := 0.25; %%% extra namespaces for boxed names newinternal nextra, niextra; numeric nextra, niextra; nextra := 2u; niextra := nextra+sdtbs; %%% extra namespace for attribute names newinternal ndextra; numeric ndextra; ndextra := nextra+dotdiam; %%% calculates mid-point on a path like |_ (vertical, horizontal) %%% final points are: z$, z$vh, z$$, where z$vh=(x$,y$$) def VH(suffix $, $$) = z$vh=(x$,y$$); enddef; %%% Calculates mid-points on a path like |_ %%% | (vertical, horizontal, vertical) %%% final points are: z$, z$vhv, z$$vhv, z$$ def VhV(suffix $, $$) = y$$vhv=1/2[y$,y$$]; x$$vhv=x$$; z$vhv=(x$,y$$vhv); enddef; %%% Calculates mid-points on a path like -|_ (horizontal, vertical, horizontal) %%% final points are: z$, z$hvh, z$$hvh, z$$ def HvH(suffix $, $$) = x$hvh=1/2[x$,x$$]; y$hvh=y$; z$$hvh=(x$hvh,y$$); enddef; %%% Calculates turning points on a U shaped path (vertical, horizontal, vertical) %%% final points are: z$, z$vyv, z$$vyv, z$$ def VyV(suffix $, @, $$) = z$$vyv=(x$$,y@); z$vyv =(x$, y@); enddef; %%% Calculates corner points rotated U shaped path (horizontal, vertical, horizontal) %%% final points are: z$, z$hxh, z$$hxh, z$$ def HxH(suffix $, @, $$) = z$$hxh=(x@,y$$); z$hxh =(x@,y$); enddef; %%% calculates length taken up by typesetting str, plus margin def namespace(text str)(expr margin) = (xpart lrcorner(str) - xpart llcorner(str) + margin) enddef; def dashes = dashed evenly enddef; def dots = dashed withdots enddef; def dashedgrid(expr nx, ny, dist) = save zg_, zg__, oldpen; pair zg_[], zg__[]; pen oldpen; oldpen = currentpen; pickup thinpen; for i = 0 upto nx: zg_[i] = (i*dist, 0); zg_[i+1000] = (i*dist, ny*dist); draw zg_[i]--zg_[i+1000] dashes; label.bot(decimal(i), zg_[i]); endfor for i = 0 upto ny: zg__[i] = (0, i*dist); zg__[i+1000] = (nx*dist, i*dist); draw zg__[i]--zg__[i+1000] dashes; label.lft(decimal(i), zg__[i]); endfor pickup oldpen; enddef; %%% draw a 1cm spaced grid of 16(x) by 21(y) cms. (units are mm) def drawgrid = dashedgrid(16, 21, 10mm); enddef; %%% calculates corner and midpoints of a rectangle, %%% bottom left at $, length l, height h def rectpoints(suffix $)(expr l, h) = z$bl = z$; z$tr = (x$+l, y$+h); z$br = (x$tr, y$bl); z$tl = (x$bl, y$tr); z$ml = 1/2[z$bl, z$tl]; z$mr = 1/2[z$br, z$tr]; z$bm = 1/2[z$bl, z$br]; z$tm = 1/2[z$tl, z$tr]; enddef; %%% calculate corner, midpoints and center point of a rhomboid. def rhompoints(suffix $)(expr l, h, s) = save eshift; numeric eshift; eshift = s*h; z$bl = z$; z$tr = (x$+l+eshift, y$+h); z$br = (x$bl+l, y$bl); z$tl = (x$bl+eshift, y$tr); z$ml = 1/2[z$bl, z$tl]; z$mr = 1/2[z$br, z$tr]; z$bm = (1/2[x$ml,x$mr], y$bl); z$tm = (x$bm, y$tr); enddef; %%% calculate circumferential points on a circle def circpoints(suffix $)(expr diam) = save rad, sinrad, cosrad; numeric rad, sinrad, cosrad; rad = diam/2; sinrad = rad*(sind 45); cosrad = rad*(cosd 45); z$c=z$; z$ml=(x$c-rad, y$c); z$mr=(x$c+rad, y$c); z$bm=(x$c, y$c-rad); z$tm=(x$c, y$c+rad); z$tr=(x$c+cosrad, y$c+sinrad); z$bl=(x$c-cosrad, y$c-sinrad); z$br=(x$tr, y$bl); z$tl=(x$bl, y$tr); enddef; %%% circular arc join between two paths tertiarydef p ~ q = begingroup c_ := fullcircle scaled 2smoothrad shifted point 0 of q; a_ := ypart(c_ intersectiontimes p); b_ := ypart(c_ intersectiontimes q); if a_ < 0: point 0 of p{direction 0 of p} else: subpath(0,a_) of p fi ... if b_ < 0: {direction infinity of q}point infinity of q else: subpath(b_,infinity) of q fi endgroup enddef; %%% piecewise linear path between the given points def sharply(text t) = % t is a list of pairs hide(n_:=0; for z=t: z_[incr n_]:=z; endfor) z_1 for k=2 upto n_: --z_[k] endfor enddef; %%% piecewise linear path between the given points with smooth corners def smoothly(text t) = % t is a list of pairs hide(n_:=0; for z=t: z_[incr n_]:=z; endfor) (z_1 for k=2 upto n_-1: --z_[k]) ~ (z_[k] endfor --z_[n_]) enddef; %%% Draw an open circle at end of vector from $ to $$ def drawO(suffix $, $$) = begingroup save v_, c_, l, p; pair v_, c_; numeric l; path p; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (dotdiam/(2l))[z$$,z$]; p := fullcircle scaled dotdiam shifted c_; unfill p; draw p; draw p; endgroup enddef; %%% Draw a closed circle at end of vector from $ to $$ def drawD(suffix $, $$) = begingroup save v_, c_, l, p; pair v_, c_; numeric l; path p; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (dotdiam/(2l))[z$$,z$]; p := fullcircle scaled dotdiam shifted c_; fill p; endgroup enddef; %%% draw an open arrowhead at end of vector from $ to $$ def drawOA(suffix $, $$) = begingroup save v_, c_, v_u, c_t, c_b, l, hb, p; pair v_, c_, v_u, c_t, c_b; numeric l, hb; path p; hb := gab/2; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (gal/(l))[z$$,z$]; % base of arrowhead v_u := unitvector v_; c_t := c_ shifted (-hb*(ypart v_u), hb*(xpart v_u)); c_b - c_ = c_ - c_t; p = c_b--z$$--c_t--cycle; unfill p; draw p; draw p; endgroup enddef; %%% draw a closed arrowhead at end of vector from $ to $$ def drawCA(suffix $, $$) = begingroup save v_, c_, v_u, c_t, c_b, l, hb, p; pair v_, c_, v_u, c_t, c_b; numeric l, hb; path p; hb := gab/2; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (gal/(l))[z$$,z$]; % base of arrowhead v_u := unitvector v_; c_t := c_ shifted (-hb*(ypart v_u), hb*(xpart v_u)); c_b - c_ = c_ - c_t; p = c_b--z$$--c_t--cycle; filldraw p; endgroup enddef; %%% draw a simple arrowhead at end of vector from $ to $$ def drawA(suffix $, $$) = begingroup save v_, c_, v_u, c_t, c_b, l, hb, p; pair v_, c_, v_u, c_t, c_b; numeric l, hb; path p; hb := gab/2; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (gal/(l))[z$$,z$]; % base of arrowhead v_u := unitvector v_; c_t := c_ shifted (-hb*(ypart v_u), hb*(xpart v_u)); c_b - c_ = c_ - c_t; p = c_b--z$$--c_t; draw p; endgroup enddef; %%% draws a fanin at the end of the vector from $ to $$ def drawF(suffix $, $$) = begingroup save v_, c_, v_u, c_t, c_b, l, hb, p; pair v_, c_, v_u, c_t, c_b; numeric l, hb; path p; hb := gfb/2; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (gfl/(l))[z$$,z$]; % apex of fan v_u := unitvector v_; c_t := z$$ shifted (-hb*(ypart v_u), hb*(xpart v_u)); c_b - z$$ = z$$ - c_t; p = c_b--c_--c_t; draw p; endgroup enddef; %%% Draw a dotted line from $ to $$ def drawdots(suffix $, $$) = pickup dotspen; draw z$--z$$ dots; pickup normalpen; enddef; %%% Draws the dotted line $--@--$$ def drawdotsthree(suffix $, @, $$) = pickup dotspen; draw z$--z@--z$$ dots; pickup normalpen; enddef; %%% Draw the dotted line $--@--@@--$$ def drawdotsfour(suffix $, @, @@, $$) = pickup dotspen; draw z$--z@--z@@--z$$ dots; pickup normalpen; enddef; %%% Draw a dotted line from $ to $$ with open circle at $$ def drawdotsO(suffix $, $$) = pickup dotspen; draw z$--z$$ dots; pickup normalpen; drawO($, $$); enddef; %%% Draws the dotted line $--@--$$ def drawdotsthreeO(suffix $, @, $$) = pickup dotspen; draw z$--z@--z$$ dots; pickup normalpen; drawO(@, $$); enddef; %%% Draw the dotted line $--@--@@--$$ def drawdotsfourO(suffix $, @, @@, $$) = pickup dotspen; draw z$--z@--z@@--z$$ dots; pickup normalpen; drawO(@@, $$); enddef; %%% Draw the dotted line from $ to $$, ending in circles diameter dotdiam at $ and $$ def drawdotsOO(suffix $, $$) = pickup dotspen; draw z$--z$$ dots; pickup normalpen; drawO($, $$); drawO($$, $); enddef; %%% draws a dashed line from $ to $$ def drawdash(suffix $, $$) = draw z$--z$$ dashes; enddef; %%% draws the dashed line $--@--$$ def drawdashthree(suffix $, @, $$) = draw z$--z@--z$$ dashes; enddef; %%% draws the dashed line $--@--@@--$$ def drawdashfour(suffix $, @, @@, $$) = draw z$--z@--z@@--z$$ dashes; enddef; %%% draws a dashed line from $ to $$, ending in a circle diameter dotdiam at $$ def drawdashO(suffix $, $$) = draw z$--z$$ dashes; drawO($, $$); enddef; %%% draws the dashed line $--@--$$ with circle at $$ def drawdashthreeO(suffix $, @, $$) = draw z$--z@--z$$ dashes; drawO(@, $$); enddef; %%% draws the dashed line $--@--@@--$$ with circle at $$ def drawdashfourO(suffix $, @, @@, $$) = draw z$--z@--z@@--z$$ dashes; drawO(@@, $$); enddef; %%% draws a dashed line from $ to $$, ending in circles diameter dotdiam at $ and $$ def drawdashOO(suffix $, $$) = draw z$--z$$ dashes; drawO($, $$); drawO($$, $); enddef; %%% draws a normal line from $ to $$. def drawnormal(suffix $, $$) = draw z$--z$$; enddef; %%% draws the normal line $--@--$$ def drawnormalthree(suffix $, @, $$) = draw z$--z@--z$$; enddef; %%% draws the normal line $--@--@@--$$ def drawnormalfour(suffix $, @, @@, $$) = draw z$--z@--z@@--z$$; enddef; %%% draws a normal line from $ to $$, ending in a circle diameter dotdiam at $$ def drawnormalO(suffix $, $$) = draw z$--z$$; drawO($, $$); enddef; %%% draws the normal line $--@--$$, ending in a circle at $$ def drawnormalthreeO(suffix $, @, $$) = draw z$--z@--z$$; drawO(@, $$); enddef; %%% draws the line $--@--@@--$$, ending in a circle at $$ def drawnormalfourO(suffix $, @, @@, $$) = draw z$--z@--z@@--z$$; drawO(@@, $$); enddef; %%% draws a normal line from $ to $$, ending in circles diameter dotdiam at $ and $$ def drawnormalOO(suffix $, $$) = draw z$--z$$; drawO($, $$); drawO($$, $); enddef; %%% draws a normal line from $ to $$, ending in a dot diameter dotdiam at $$ def drawnormalD(suffix $, $$) = draw z$--z$$; drawD($, $$); enddef; %%% draws the normal line $--@--$$, ending in a dot at $$ def drawnormalthreeD(suffix $, @, $$) = draw z$--z@--z$$; drawD(@, $$); enddef; %%% draws the normal line $--@--@@--$$, ending in a dot at $$ def drawnormalfourD(suffix $, @, @@, $$) = draw z$--z@--z@@--z$$; drawD(@@, $$); enddef; %%% draws a normal line from $ to $$, ending in dots diameter dotdiam at $ and $$ def drawnormalDD(suffix $, $$) = draw z$--z$$; drawD($, $$); drawD($$, $); enddef; %%% draws a normal line from $ to $$, ending with an open arrowhead at $$ def drawnormalOA(suffix $, $$) = draw z$--z$$; drawOA($, $$); enddef; %%% draws a normal line from $ to $$, ending with a closed arrowhead at $$ def drawnormalCA(suffix $, $$) = draw z$--z$$; drawCA($, $$); enddef; %%% draws the normal line $--@--$$, ending in a black arrowhead at $$ def drawnormalthreeCA(suffix $, @, $$) = draw z$--z@--z$$; drawCA(@, $$); enddef; %%% draws the normal line $--@--@@--$$, ending in a black arrowhead at $$ def drawnormalfourCA(suffix $, @, @@, $$) = draw z$--z@--z@@--z$$; drawCA(@@, $$); enddef; %%% draws a normal line from $ to $$, ending with a fanin at $$ def drawnormalF(suffix $, $$) = draw z$--z$$; drawF($, $$); enddef; %%% draws a normal line from $ to $$, with a fanin at $ and an open circle at $$ def drawnormalFO(suffix $, $$) = draw z$--z$$; drawO($, $$); drawF($$, $); enddef; %%% draws a thick line from $ to $$. def drawthick(suffix $, $$) = pickup thickpen; draw z$--z$$; pickup normalpen; enddef; %%% draws a thick line from $ to $$, ending in a circle diameter dotdiam at $$ def drawthickO(suffix $, $$) = pickup thickpen; draw z$--z$$; drawO($, $$); pickup normalpen; enddef; %%% draws a thick line from $ to $$, ending in circles diameter dotdiam at $ and $$ def drawthickOO(suffix $, $$) = pickup thickpen; draw z$--z$$; drawO($, $$); drawO($$, $); pickup normalpen; enddef; %%% replaces the sharp corner on $--@--$$ with a circular arc radius smoothrad def smooth(suffix $, @, $$) = begingroup save v_, c_, l, p; pair v_, v_', c_, c_'; path p; v_ := z@-z$; l := (xpart v_)++(ypart v_); % length of $--@ c_ := (smoothrad/l)[z@,z$]; % start of arc on $--@ v_' := z$$-z@; l := (xpart v_')++(ypart v_'); % length of @--$$ c_' := (smoothrad/l)[z@,z$$]; % end of arc on @--$$ undraw c_--z@--c_'; % blank original join draw c_{v_}..{v_'}c_'; % draw the arc endgroup enddef; %%% replaces the sharp corners on $--@--@@--$$ with a circular arc radius smoothrad def smoothtwo(suffix $, @, @@, $$) = smooth($, @, @@); smooth(@, @@, $$); enddef; %%% replaces the sharp corner on the dashed lines $--@--$$ %%% with a circular arc radius smoothrad def smoothdash(suffix $, @, $$) = begingroup save v_, c_, l, p; pair v_, v_', c_, c_'; path p; v_ := z@-z$; l := (xpart v_)++(ypart v_); % length of $--@ c_ := (smoothrad/l)[z@,z$]; % start of arc on $--@ v_' := z$$-z@; l := (xpart v_')++(ypart v_'); % length of @--$$ c_' := (smoothrad/l)[z@,z$$]; % end of arc on @--$$ undraw c_--z@--c_'; % blank original join draw c_{v_}..{v_'}c_' dashes; % draw the dashed arc endgroup enddef; %%% replaces the sharp corner on the dotted line $--@--$$ %%% with a circular arc radius smoothrad def smoothdots(suffix $, @, $$) = begingroup save oldpen; pen oldpen; oldpen := currentpen; save v_, c_, l, p; pair v_, v_', c_, c_'; path p; v_ := z@-z$; l := (xpart v_)++(ypart v_); % length of $--@ c_ := (smoothrad/l)[z@,z$]; % start of arc on $--@ v_' := z$$-z@; l := (xpart v_')++(ypart v_'); % length of @--$$ c_' := (smoothrad/l)[z@,z$$]; % end of arc on @--$$ undraw c_--z@--c_'; % blank original join pickup dotspen; draw c_{v_}..{v_'}c_' dots; % draw the dotted arc pickup oldpen; endgroup enddef; %%% draws a schema box, bottom left at $, length l, height h def drawSCHEMA(suffix $)(expr l, h)(text str) = rectpoints($, l, h); x$c = 1/2[x$ml, x$mr]; y$c = 1/2[y$ml, y$tl]; draw z$bl--z$br--z$tr--z$tl--cycle; % outer box draw z$ml--z$mr; % dividing line label(str, z$c); enddef; def drawSDT(suffix $)(text str) = rectpoints($, sdtbl, sdtbh); z$ti = (x$tr-sdtbs, y$tr); z$bi = (x$ti, y$br); z$c = 1/2[z$bl,z$ti]; draw z$bl--z$br--z$tr--z$tl--cycle; draw z$bi--z$ti; label(str, z$c); enddef; def drawASDT(suffix $)(expr l, h)(text str) = rectpoints($, l, h); z$ti = (x$tr-sdtbs, y$tr); z$bi = (x$ti, y$br); z$c = 1/2[z$bl,z$ti]; draw z$bl--z$br--z$tr--z$tl--cycle; draw z$bi--z$ti; label(str, z$c); enddef; def drawBINARY(suffix $) = drawASDT($)(sdtbl, sdtbh)("BINARY"); enddef; def drawBOOLEAN(suffix $) = drawASDT($)(sdtbl, sdtbh)("BOOLEAN"); enddef; def drawCOMPLEX(suffix $) = drawASDT($)(sdtbl, sdtbh)("COMPLEX"); enddef; def drawEXPRESSION(suffix $) = drawASDT($)(sdtbel, sdtbeh)("EXPRESSION"); enddef; def drawGENERIC(suffix $) = drawASDT($)(sdtbl, sdtbh)("GENERIC"); enddef; def drawINTEGER(suffix $) = drawASDT($)(sdtbl, sdtbh)("INTEGER"); enddef; def drawLOGICAL(suffix $) = drawASDT($)(sdtbl, sdtbh)("LOGICAL"); enddef; def drawNUMBER(suffix $) = drawASDT($)(sdtbl, sdtbh)("NUMBER"); enddef; def drawREAL(suffix $) = drawASDT($)(sdtbl, sdtbh)("REAL"); enddef; def drawSTRING(suffix $) = drawASDT($)(sdtbl, sdtbh)("STRING"); enddef; %%% draw an enumeration type box, bottom left at $, length l, height h def drawENUM(suffix $)(expr l, h)(text str) = rectpoints($, l, h); z$ti = (x$tr-sdtbs, y$tr); z$bi = (x$ti, y$br); z$c = 1/2[z$bl,z$ti]; draw z$bl--z$br--z$tr--z$tl--cycle dashes; draw z$bi--z$ti dashes; label(str, z$c); enddef; %%% draw a select type box, bottom left at $, length l, height h def drawSELECT(suffix $)(expr l, h)(text str) = rectpoints($, l, h); z$ti = (x$tl+sdtbs, y$tl); z$bi = (x$ti, y$bl); z$c = 1/2[z$br,z$ti]; draw z$bl--z$br--z$tr--z$tl--cycle dashes; draw z$bi--z$ti dashes; label(str, z$c); enddef; %%% draw a simple user defined TYPE box, bottom left at $, length l, height h def drawTYPE(suffix $)(expr l, h)(text str) = rectpoints($, l, h); z$c = 1/2[z$bl,z$tr]; draw z$bl--z$br--z$tr--z$tl--cycle dashes; label(str, z$c); enddef; %%% draw an entity box, bottom left at $, length l, height h def drawENT(suffix $)(expr l, h)(text str) = rectpoints($, l, h); z$c = 1/2[z$bl,z$tr]; draw z$bl--z$br--z$tr--z$tl--cycle; label(str, z$c); enddef; def drawOB(suffix $)(expr l, h) = save rad; numeric rad; rad := h/2; rectpoints($, l, h); z$cl = 1/2[z$bl, z$tl]; z$cr = 1/2[z$br, z$tr]; z$bli = (x$bl+rad, y$bl); z$tli = (x$bli, y$tl); z$bri = (x$br-rad, y$br); z$tri = (x$bri, y$tr); z$c = 1/2[z$bl,z$tr]; draw z$bli--z$bri..z$cr..z$tri--z$tli..z$cl..cycle; enddef; %%% draw a page reference box oval, bottom left at $, length l, height h def drawPREF(suffix $)(expr l, h)(text str) = drawOB($, l, h); label(str, z$c); enddef; %%% draw an interschema USE box, bottom left at $, length l, height h def drawISU(suffix $)(expr l, h)(text str) = save quarter; numeric quarter; quarter := h/4; rectpoints($, l, h); z$o = (x$, y$+quarter); drawOB($o, l, 2quarter); z$c = 1/2[z$bl,z$tr]; label(str, z$c); draw z$bl--z$br--z$tr--z$tl--cycle; enddef; %%% draw an interschema USE RENAME box, bottom left at $, length l, height h def drawISUR(suffix $)(expr l, h)(text str, rname) = save third; numeric third; third := h/3; rectpoints($, l, h); z$o = (x$, y$+third); drawOB($o, l, third); z$c = 1/2[z$bl, z$tr]; label(str, z$c); z$rnm = 1/2[z$bl,(x$br,y$br+third)]; draw z$bl--z$br--z$tr--z$tl--cycle; label(rname, z$rnm); enddef; %%% draw an interschema REFERENCE box, bottom left at $, length l, height h def drawISR(suffix $)(expr l, h)(text str) = save quarter; numeric quarter; quarter := h/4; rectpoints($, l, h); z$o = (x$, y$+quarter); drawOB($o, l, 2quarter); z$c = 1/2[z$bl,z$tr]; label(str, z$c); draw z$bl--z$br--z$tr--z$tl--cycle dashes; enddef; %%% draw an interschema REFERENCE RENAME box, bottom left at $, length l, height h def drawISRR(suffix $)(expr l, h)(text str, rname) = save third; numeric third; third := h/3; rectpoints($, l, h); z$o = (x$, y$+third); drawOB($o, l, third); z$c = 1/2[z$bl,z$tr]; label(str, z$c); z$rnm = 1/2[z$bl,(x$br,y$br+third)]; draw z$bl--z$br--z$tr--z$tl--cycle dashes; label(rname, z$rnm); enddef; %%% draw a Local EVENT box, bottom left at $, length l, height h def drawLEVENT(suffix $)(expr l, h)(text str) = rhompoints($, l, h, eventslope); z$c = 1/2[z$ml,z$mr]; draw z$bl--z$br--z$tr--z$tl--cycle; label(str, z$c); enddef; %%% draw a Global EVENT box, bottom left at $, length l, height h def drawGEVENT(suffix $)(expr l, h)(text str) = rhompoints($, l, h, eventslope); z$c = 1/2[z$ml,z$mr]; pickup thickpen; draw z$bl--z$br--z$tr--z$tl--cycle; pickup normalpen; label(str, z$c); enddef; %%% draw a circled name, diameter diam centered at $ def drawcirclebox(suffix $)(expr diam)(text str) = circpoints($, diam); draw z$bl..z$bm..z$br..z$mr..z$tr..z$tm..z$tl..z$ml..cycle; label(str, z$c); enddef; %%% length and base width of diamond line end styles newinternal gdl, gdb; numeric gdl, gdb; gdl := 2defaultgal; gdb := 0.75defaultgab; def ellipsepoints(suffix $)(expr l, h) = save epp, move; path epp; pair move; z$ml=(x$-l/2, y$); z$mr=(x$ml+l,y$); z$tm=(x$, y$+h/2); z$bm=(x$, y$tm-h); move = 1/2[z$ml,z$mr]; epp = fullcircle scaled h xscaled (l/h) shifted move; z$tr = point 1.2 of epp; z$tl = point 2.8 of epp; z$bl = point 5.2 of epp; z$br = point 6.8 of epp; enddef; %%% draws double closed arrowheads at end of vector from $ to $$ def drawDCA(suffix $, $$) = begingroup save v_, c_, v_u, c_t, c_b, l, hb, p; pair v_, c_, v_u, c_t, c_b; path p[]; numeric l, hb; hb := gab/2; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (gal/(l))[z$$,z$]; % base of arrowhead v_u := unitvector v_; c_t := c_ shifted (-hb*(ypart v_u), hb*(xpart v_u)); c_b - c_ = c_ - c_t; p1 := c_b--z$$--c_t--cycle; filldraw p1; p2 := p1 shifted ((xpart c_ - x$$), (ypart c_ - y$$)); filldraw p2; endgroup enddef; %%% draws an open diamond at end of vector from $ to $$ def drawOD(suffix $, $$) = begingroup save v_, c_, c__, v_u, c_t, c_b, l, hb, p; pair v_, c_, c__, v_u, c_t, c_b; numeric l, hb; path p; hb := gdb/2; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (gdl/(2l))[z$$,z$]; % base of diamond c__ := (gdl/(l))[z$$,z$]; % interior tip of diamond v_u := unitvector v_; c_t := c_ shifted (-hb*(ypart v_u), hb*(xpart v_u)); c_b - c_ = c_ - c_t; p = c_b--z$$--c_t--c__--cycle; unfill p; draw p; draw p; endgroup enddef; %%% draws a closed diamond at end of vector from $ to $$ def drawCD(suffix $, $$) = begingroup save v_, c_, c__, v_u, c_t, c_b, l, hb, p; pair v_, c_, c__, v_u, c_t, c_b; numeric l, hb; path p; hb := gdb/2; v_ := z$-z$$; l := (xpart v_)++(ypart v_); % length of the line c_ := (gdl/(2l))[z$$,z$]; % base of diamond c__ := (gdl/(l))[z$$,z$]; % interior tip of diamond v_u := unitvector v_; c_t := c_ shifted (-hb*(ypart v_u), hb*(xpart v_u)); c_b - c_ = c_ - c_t; p = c_b--z$$--c_t--c__--cycle; filldraw p; endgroup enddef; %%% draws a dashed line from $ to $$, ending with an arrowhead at $$ def drawdashA(suffix $, $$) = draw z$--z$$ dashes; drawA($, $$); enddef; %%% draws a dashed line from $ to $$, ending with an open arrowhead at $$ def drawdashOA(suffix $, $$) = draw z$--z$$ dashes; drawOA($, $$); enddef; %%% draws a normal line from $ to $$, ending with double closed arrowheads at $$ def drawnormalDCA(suffix $, $$) = draw z$--z$$; drawDCA($, $$); enddef; %%% draws a normal line from $ to $$, ending with an open diamond at $$ def drawnormalOD(suffix $, $$) = draw z$--z$$; drawOD($, $$); enddef; %%% draws a normal line from $ to $$, ending with a closed diamond at $$ def drawnormalCD(suffix $, $$) = draw z$--z$$; drawCD($, $$); enddef; %%% draws an open dashed circle, center z$, diameter diam def drawdashcircle(suffix $)(expr diam) = circpoints($, diam); draw z$bl..z$bm..z$br..z$mr..z$tr..z$tm..z$tl..z$ml..cycle dashes; enddef; %%% draws an open circle, center z$, diameter diam, with an arrow at the top def drawcircleA(suffix $)(expr diam) = circpoints($, diam); begingroup save c_, c_t, c_b, hb; pair c_, c_t, c_b; numeric hb; hb := gab/2; c_ := z$tm shifted (gal*right); % base of arrowhead c_t := c_ shifted (hb*up); c_b := c_ shifted (hb*down); draw z$bl..z$bm..z$br..z$mr..z$tr..z$tm..z$tl..z$ml..cycle; draw c_t--z$tm--c_b; endgroup enddef; %%% draws black dot, center z$, diameter diam def drawDot(suffix $)(expr diam) = begingroup save p; path p; p := fullcircle scaled diam shifted z$; filldraw p; endgroup enddef; %%% draws black dot surrounded by a circle, center z$, diameter diam def drawCircledDot(suffix $)(expr diam) = begingroup save l_, p; numeric l_; path p[]; l_ := 5/7diam; p1 := fullcircle scaled diam shifted z$; unfill p1; draw p1; p2 := fullcircle scaled l_ shifted z$; filldraw p2; endgroup enddef; def drawcardbox(suffix $)(expr l, h, m)(text str) = rectpoints($, l, h); begingroup save c; pair c[]; c1 = (x$tr-m, y$tr); c3 = (x$tr, y$tr-m); c2 = (xpart c1, ypart c3); draw z$bl--z$br--c3--c1--z$tl--cycle; draw c1--c2--c3; endgroup; z$c = 1/2[z$ml,z$mr]; label(str, z$c); enddef; def drawdiamondbox(suffix $)(expr l, h)(text str) = z$ml=(x$-l/2, y$); z$tm=(x$, y$+h/2); z$mr=(x$ml+l, y$); z$bm=(x$, y$tm-h); z$bl=1/2[z$ml,z$bm]; z$br=1/2[z$bm,z$mr]; z$tr=1/2[z$mr,z$tm]; z$tl=1/2[z$tm,z$ml]; z$c=z$; draw z$ml--z$bm--z$mr--z$tm--cycle; label(str, z$c); enddef; def drawtwodiamondbox(suffix $)(expr l, h, mrg)(text str) = z$ml=(x$-l/2, y$); z$tm=(x$, y$+h/2); z$mr=(x$ml+l, y$); z$bm=(x$, y$tm-h); z$bl=1/2[z$ml,z$bm]; z$br=1/2[z$bm,z$mr]; z$tr=1/2[z$mr,z$tm]; z$tl=1/2[z$tm,z$ml]; z$c=z$; begingroup save v_, p, tl, sf; pair v_; numeric tl, sf; path p[]; p1 = z$ml--z$bm--z$mr--z$tm--cycle; draw p1; v_ := z$c-z$tr; tl := (xpart v_)++(ypart v_); sf = 1.0 - mrg/tl; p2 = p1 shifted -z$c scaled sf shifted z$c; draw p2; endgroup; label(str, z$c); enddef; def drawdoublerectangle(suffix $)(expr l, h, tf) = rectpoints($, l, h); z$tfl=tf[z$tl,z$bl]; z$tfr=tf[z$tr,z$br]; z$cb=1/2[z$bl,z$tfr]; z$ct=1/2[z$tfl,z$tr]; draw z$bl--z$br--z$tr--z$tl--cycle; draw z$tfl--z$tfr; enddef; def drawtriplerectangle(suffix $)(expr l, h, tf, bf) = rectpoints($, l, h); z$tfl=tf[z$tl,z$bl]; z$tfr=tf[z$tr,z$br]; z$bfl=bf[z$bl,z$tl]; z$bfr=bf[z$br,z$tr]; z$cb=1/2[z$bl,z$bfr]; z$cm=1/2[z$bfl,z$tfr]; z$ct=1/2[z$tfl,z$tr]; draw z$bl--z$br--z$tr--z$tl--cycle; draw z$bfl--z$bfr; draw z$tfl--z$tfr; enddef; def hiderectangle(suffix $)(expr l, h) = begingroup save c; pair c[]; c1=(x$,y$); c2=c1+(l,0); c3=c1+(l,h); c4=c1+(0,h); unfilldraw c1--c2--c3--c4--cycle; endgroup enddef; def drawdashboxover(suffix $)(expr l, h) = rectpoints($, l, h); hiderectangle($, l, h); z$c = 1/2[z$bl,z$tr]; draw z$bl--z$br--z$tr--z$tl--cycle dashes; enddef; def drawindexbox(suffix $)(expr l, h, lp, hp)(text str) = rectpoints($, l, h); z$c = 1/2[z$bl,z$tr]; z$P = z$tl; rectpoints($P, lp, hp); z$P.c = 1/2[z$P.bl, z$P.tr]; draw z$bl--z$br--z$tr--z$tl--cycle; draw z$P.bl--z$P.br--z$P.tr--z$P.tl--cycle; label(str, z$P.c); enddef; def drawroundedbox(suffix $)(expr l, h, r)(text str) = rectpoints($, l, h); begingroup save rad; numeric rad; rad := r; if rad > l/2: rad := l/2; fi if rad > h/2: rad := h/2; fi draw (x$br-rad, y$br){right}..{up}(x$br, y$br+rad)-- (x$tr, y$tr-rad){up}..{left}(x$tr-rad, y$tr)-- (x$tl+rad, y$tl){left}..{down}(x$tl, y$tl-rad)-- (x$bl, y$bl+rad){down}..{right}(x$bl+rad, y$bl)--cycle; endgroup; z$c = 1/2[z$bl,z$tr]; label(str, z$c); enddef; def drawovalbox(suffix $)(expr l, h)(text str) = ellipsepoints($, l, h); z$c = 1/2[z$ml,z$mr]; begingroup save p; path p; p = fullcircle scaled h xscaled (l/h) shifted z$c; draw p; endgroup; label(str, z$c); enddef; def drawdashellipse(suffix $)(expr l, h) = ellipsepoints($, l, h); z$c = 1/2[z$ml,z$mr]; begingroup save p; path p; p = fullcircle scaled h xscaled (l/h) shifted z$c; draw p dashes; endgroup enddef; def drawdrum(suffix $)(expr l, h)(text str) = save vdia; numeric vdia; vdia := drumlid*l; % ellipse vertical diameter save pf, ph; path pf, ph; % full & half ellipse paths % points on the basic rectangle z$bl = z$; z$tr = (x$+l, y$+h); z$br = (x$tr, y$); z$tl = (x$, y$tr); z$ml = 1/2[z$bl,z$tl]; z$mr = 1/2[z$br,z$tr]; z$tc = 1/2[z$tl,z$tr]; % center of top rectangle line z$bc = 1/2[z$bl,z$br]; % draw box sides draw z$tl--z$bl; draw z$tr--z$br; % points on top ellipse z$T''' = z$tc; % ellipse center ellipsepoints($T''', l, vdia); z$tm = z$T'''.tm; z$tml = z$T'''.tl; z$tmr = z$T'''.tr; % points on bottom ellipse z$B''' = z$bc; ellipsepoints($B''', l, vdia); z$bm = z$B'''.bm; z$bml = z$B'''.bl; z$bmr = z$B'''.br; % box center point z$c = 1/2[z$T'''.bm, z$B'''.bm]; % draw top ellipse pf = fullcircle scaled vdia xscaled (l/vdia) shifted z$T'''; draw pf; % draw bottom half ellipse ph = (halfcircle rotated 180) scaled vdia xscaled (l/vdia) shifted z$B'''; draw ph; label(str, z$c); enddef; def drawoutputbox(suffix $)(expr l, h)(text str) = rectpoints($, l, h); begingroup save c; pair c[]; c1 = (x$br, y$br+1/8h); % right side of box is shorter c2 = (x$bm, y$bm+1/16h); % draw the tear draw z$bl..c2{dir 45}..c1{dir -15}--z$tr--z$tl--cycle; endgroup; z$c = (x$bm, 1/2(y$bm+y$tm)); label(str, z$c); enddef; \def drawstickman(suffix $)(expr l, h) = rectpoints($,l,h); begingroup save c; pair c[]; c1 = 8/24[z$bm,z$tm]; c2 = 15/24[z$bm,z$tm]; c3 = 18/24[z$bm,z$tm]; c4 = 1/2[c3,z$tm]; c6 = (x$bl, ypart(c2)); c7 = (x$br, ypart(c2)); draw z$bl--c1--z$br; % legs draw c1--c3; % body draw c6--c7; % arms draw c3{right}..z$tm{left}..cycle; % head endgroup; enddef;