blob: 999c82ef6f1074d0742704741292b98eee2fcff9 [file] [log] [blame]
###############################################################################
# #
# Lout @Diag package for drawing diagrams #
# Version 1.1 (February 2000) #
# Jeffrey H. Kingston #
# #
# Version 1.0 (July 1996) #
# Based on Version 2.0 of the @Fig package (Jeffrey H. Kingston, Dec 1992). #
# #
###############################################################################
@SysPrependGraphic { diagf.lpg }
@SysInclude { diagf.etc }
###############################################################################
# #
# @DiagSetup symbol #
# #
###############################################################################
export @Diag @SyntaxDiag
def @DiagSetup
named save { no }
named maxlabels { 200 }
named title { "--titledft--" }
named titleformat
left @Title
right @Body
{ Italic @Font @Title //0.7f ||0.35f @Body }
###########################################################################
# #
# @Node options of @DiagSetup #
# #
###########################################################################
import @Geometry named outline
named margin {}
named shadow {}
named sides {}
named angle {}
{ box }
named margin { 0.6f }
import @Geometry named shadow { 0.4f }
import @Geometry named sides { 3 }
import @Geometry named angle { "dup 180 exch div" }
named translate { }
named outlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ solid }
import @Geometry named outlinedashlength { 0.2f }
import @Geometry named outlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ thin }
named paint { nopaint }
named font { }
named break { }
named format right @Body { @Body }
named valign { ctr }
named vsize { }
named vindent { ctr }
named vstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named vmargin { }
named topmargin { }
named footmargin { }
named halign { ctr }
named hsize { }
named hindent { ctr }
named hstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named hmargin { }
named leftmargin { }
named rightmargin { }
named nodelabel { }
named nodelabelmargin { 0.2f }
named nodelabelfont { -2p }
named nodelabelbreak { ragged nohyphen }
named nodelabelformat right @Body { @Body }
import @Geometry named nodelabelpos { }
named nodelabelprox { outside }
import @Geometry named nodelabelangle { horizontal }
named nodelabelctr { no }
import @Geometry named nodelabeladjust { 0 0 }
named alabel { }
named alabelmargin { }
named alabelfont { }
named alabelbreak { }
named alabelformat right @Body { }
import @Geometry named alabelpos { NE }
named alabelprox { }
import @Geometry named alabelangle { }
named alabelctr { }
import @Geometry named alabeladjust { }
named blabel { }
named blabelmargin { }
named blabelfont { }
named blabelbreak { }
named blabelformat right @Body { }
import @Geometry named blabelpos { NW }
named blabelprox { }
import @Geometry named blabelangle { }
named blabelctr { }
import @Geometry named blabeladjust { }
named clabel { }
named clabelmargin { }
named clabelfont { }
named clabelbreak { }
named clabelformat right @Body { }
import @Geometry named clabelpos { SW }
named clabelprox { }
import @Geometry named clabelangle { }
named clabelctr { }
import @Geometry named clabeladjust { }
named dlabel { }
named dlabelmargin { }
named dlabelfont { }
named dlabelbreak { }
named dlabelformat right @Body { }
import @Geometry named dlabelpos { SE }
named dlabelprox { }
import @Geometry named dlabelangle { }
named dlabelctr { }
import @Geometry named dlabeladjust { }
###########################################################################
# #
# @ANode options of @DiagSetup #
# #
###########################################################################
import @Geometry named aoutline
named margin {}
named shadow {}
named sides {}
named angle {}
{ box }
named amargin { 0.6f }
import @Geometry named ashadow { 0.4f }
import @Geometry named asides { 3 }
import @Geometry named aangle { "dup 180 exch div" }
named atranslate { }
named aoutlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ solid }
import @Geometry named aoutlinedashlength { 0.2f }
import @Geometry named aoutlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ thin }
named apaint { nopaint }
named afont { }
named abreak { }
named aformat right @Body { @Body }
named avalign { ctr }
named avsize { }
named avindent { ctr }
named avstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named avmargin { }
named atopmargin { }
named afootmargin { }
named ahalign { ctr }
named ahsize { }
named ahindent { ctr }
named ahstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named ahmargin { }
named aleftmargin { }
named arightmargin { }
named anodelabel { }
named anodelabelmargin { 0.2f }
named anodelabelfont { -2p }
named anodelabelbreak { ragged nohyphen }
named anodelabelformat right @Body { @Body }
import @Geometry named anodelabelpos{ }
named anodelabelprox { outside }
import @Geometry named anodelabelangle { horizontal }
named anodelabelctr { no }
import @Geometry named anodelabeladjust { 0 0 }
named aalabel { }
named aalabelmargin { }
named aalabelfont { }
named aalabelbreak { }
named aalabelformat right @Body { }
import @Geometry named aalabelpos { NE }
named aalabelprox { }
import @Geometry named aalabelangle { }
named aalabelctr { }
import @Geometry named aalabeladjust{ }
named ablabel { }
named ablabelmargin { }
named ablabelfont { }
named ablabelbreak { }
named ablabelformat right @Body { }
import @Geometry named ablabelpos { NW }
named ablabelprox { }
import @Geometry named ablabelangle { }
named ablabelctr { }
import @Geometry named ablabeladjust{ }
named aclabel { }
named aclabelmargin { }
named aclabelfont { }
named aclabelbreak { }
named aclabelformat right @Body { }
import @Geometry named aclabelpos { SW }
named aclabelprox { }
import @Geometry named aclabelangle { }
named aclabelctr { }
import @Geometry named aclabeladjust{ }
named adlabel { }
named adlabelmargin { }
named adlabelfont { }
named adlabelbreak { }
named adlabelformat right @Body { }
import @Geometry named adlabelpos { SE }
named adlabelprox { }
import @Geometry named adlabelangle { }
named adlabelctr { }
import @Geometry named adlabeladjust{ }
###########################################################################
# #
# @BNode options of @DiagSetup #
# #
###########################################################################
import @Geometry named boutline
named margin {}
named shadow {}
named sides {}
named angle {}
{ box }
named bmargin { 0.6f }
import @Geometry named bshadow { 0.4f }
import @Geometry named bsides { 3 }
import @Geometry named bangle { "dup 180 exch div" }
named btranslate { }
named boutlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ solid }
import @Geometry named boutlinedashlength { 0.2f }
import @Geometry named boutlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ thin }
named bpaint { nopaint }
named bfont { }
named bbreak { }
named bformat right @Body { @Body }
named bvalign { ctr }
named bvsize { }
named bvindent { ctr }
named bvstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named bvmargin { }
named btopmargin { }
named bfootmargin { }
named bhalign { ctr }
named bhsize { }
named bhindent { ctr }
named bhstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named bhmargin { }
named bleftmargin { }
named brightmargin { }
named bnodelabel { }
named bnodelabelmargin { 0.2f }
named bnodelabelfont { -2p }
named bnodelabelbreak { ragged nohyphen }
named bnodelabelformat right @Body { @Body }
import @Geometry named bnodelabelpos{ }
named bnodelabelprox { outside }
import @Geometry named bnodelabelangle { horizontal }
named bnodelabelctr { no }
import @Geometry named bnodelabeladjust { 0 0 }
named balabel { }
named balabelmargin { }
named balabelfont { }
named balabelbreak { }
named balabelformat right @Body { }
import @Geometry named balabelpos { NE }
named balabelprox { }
import @Geometry named balabelangle { }
named balabelctr { }
import @Geometry named balabeladjust{ }
named bblabel { }
named bblabelmargin { }
named bblabelfont { }
named bblabelbreak { }
named bblabelformat right @Body { }
import @Geometry named bblabelpos { NW }
named bblabelprox { }
import @Geometry named bblabelangle { }
named bblabelctr { }
import @Geometry named bblabeladjust{ }
named bclabel { }
named bclabelmargin { }
named bclabelfont { }
named bclabelbreak { }
named bclabelformat right @Body { }
import @Geometry named bclabelpos { SW }
named bclabelprox { }
import @Geometry named bclabelangle { }
named bclabelctr { }
import @Geometry named bclabeladjust{ }
named bdlabel { }
named bdlabelmargin { }
named bdlabelfont { }
named bdlabelbreak { }
named bdlabelformat right @Body { }
import @Geometry named bdlabelpos { SE }
named bdlabelprox { }
import @Geometry named bdlabelangle { }
named bdlabelctr { }
import @Geometry named bdlabeladjust{ }
###########################################################################
# #
# @CNode options of @DiagSetup #
# #
###########################################################################
import @Geometry named coutline
named margin {}
named shadow {}
named sides {}
named angle {}
{ box }
named cmargin { 0.6f }
import @Geometry named cshadow { 0.4f }
import @Geometry named csides { 3 }
import @Geometry named cangle { "dup 180 exch div" }
named ctranslate { }
named coutlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ solid }
import @Geometry named coutlinedashlength { 0.2f }
import @Geometry named coutlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ thin }
named cpaint { nopaint }
named cfont { }
named cbreak { }
named cformat right @Body { @Body }
named cvalign { ctr }
named cvsize { }
named cvindent { ctr }
named cvstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named cvmargin { }
named ctopmargin { }
named cfootmargin { }
named chalign { ctr }
named chsize { }
named chindent { ctr }
named chstrut
named no { 0.0f }
named yes { 1.0f }
{ no }
named chmargin { }
named cleftmargin { }
named crightmargin { }
named cnodelabel { }
named cnodelabelmargin { 0.2f }
named cnodelabelfont { -2p }
named cnodelabelbreak { ragged nohyphen }
named cnodelabelformat right @Body { @Body }
import @Geometry named cnodelabelpos{ }
named cnodelabelprox { outside }
import @Geometry named cnodelabelangle { horizontal }
named cnodelabelctr { no }
import @Geometry named cnodelabeladjust { 0 0 }
named calabel { }
named calabelmargin { }
named calabelfont { }
named calabelbreak { }
named calabelformat right @Body { }
import @Geometry named calabelpos { NE }
named calabelprox { }
import @Geometry named calabelangle { }
named calabelctr { }
import @Geometry named calabeladjust{ }
named cblabel { }
named cblabelmargin { }
named cblabelfont { }
named cblabelbreak { }
named cblabelformat right @Body { }
import @Geometry named cblabelpos { NW }
named cblabelprox { }
import @Geometry named cblabelangle { }
named cblabelctr { }
import @Geometry named cblabeladjust{ }
named cclabel { }
named cclabelmargin { }
named cclabelfont { }
named cclabelbreak { }
named cclabelformat right @Body { }
import @Geometry named cclabelpos { SW }
named cclabelprox { }
import @Geometry named cclabelangle { }
named cclabelctr { }
import @Geometry named cclabeladjust{ }
named cdlabel { }
named cdlabelmargin { }
named cdlabelfont { }
named cdlabelbreak { }
named cdlabelformat right @Body { }
import @Geometry named cdlabelpos { SE }
named cdlabelprox { }
import @Geometry named cdlabelangle { }
named cdlabelctr { }
import @Geometry named cdlabeladjust{ }
###########################################################################
# #
# @Link options of @DiagSetup #
# #
###########################################################################
import @Geometry named path
named from {}
named to {}
named bias {}
named fbias {}
named tbias {}
named radius {}
named xindent {}
named zindent {}
named frompt {}
named topt {}
named arrow {}
named arrowlength {}
{ line }
import @Geometry named from { 0,0 }
import @Geometry named to { 1,1 }
import @Geometry named bias { 2.0f }
import @Geometry named fbias { 2.0f }
import @Geometry named tbias { 2.0f }
import @Geometry named radius { 1.0f }
import @Geometry named xindent { 0.8f }
import @Geometry named zindent { 0.8f }
import @Geometry named frompt { 0 0 }
import @Geometry named topt { 0 0 }
named pathstyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ solid }
import @Geometry named pathdashlength { 0.2f }
import @Geometry named pathwidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ thin }
import @Geometry named pathgap
named thin { 0.08 ft }
named medium { 0.16 ft }
named thick { 0.24 ft }
{ thin }
named arrow { no }
named arrowstyle { solid }
named arrowwidth { 0.3f }
named arrowlength { 0.5f }
named linklabel { }
named linklabelmargin { 0.2f }
named linklabelfont { -2p }
named linklabelbreak { ragged nohyphen }
named linklabelformat right @Body { @Body }
import @Geometry named linklabelpos { }
named linklabelprox { above }
import @Geometry named linklabelangle { horizontal }
named linklabelctr { no }
import @Geometry named linklabeladjust { 0 0 }
named xlabel { }
named xlabelmargin { }
named xlabelfont { }
named xlabelbreak { }
named xlabelformat right @Body { }
import @Geometry named xlabelpos { LFROM }
named xlabelprox { }
import @Geometry named xlabelangle { }
named xlabelctr { }
import @Geometry named xlabeladjust { }
named ylabel { }
named ylabelmargin { }
named ylabelfont { }
named ylabelbreak { }
named ylabelformat right @Body { }
import @Geometry named ylabelpos { LMID }
named ylabelprox { }
import @Geometry named ylabelangle { }
named ylabelctr { yes }
import @Geometry named ylabeladjust { }
named zlabel { }
named zlabelmargin { }
named zlabelfont { }
named zlabelbreak { }
named zlabelformat right @Body { }
import @Geometry named zlabelpos { LTO }
named zlabelprox { }
import @Geometry named zlabelangle { }
named zlabelctr { }
import @Geometry named zlabeladjust { }
named fromlabel { }
named fromlabelmargin { 0f }
named fromlabelfont { }
named fromlabelbreak { ragged nohyphen }
named fromlabelformat right @Body { @Body }
import @Geometry named fromlabelpos { FROM }
named fromlabelprox { W }
import @Geometry named fromlabelangle { antiparallel }
named fromlabelctr { no }
import @Geometry named fromlabeladjust { 0 0 }
named tolabel { }
named tolabelmargin { 0f }
named tolabelfont { }
named tolabelbreak { ragged nohyphen }
named tolabelformat right @Body { @Body }
import @Geometry named tolabelpos { TO }
named tolabelprox { W }
import @Geometry named tolabelangle { parallel }
named tolabelctr { no }
import @Geometry named tolabeladjust { 0 0 }
###########################################################################
# #
# Tree and syntax diagram options of @DiagSetup #
# #
###########################################################################
named treehsep { 0.5f }
named treevsep { 0.5f }
named treehindent
named left { 0.0rt }
named ctr { 0.5rt }
named right { 1.0rt }
{ ctr }
named treevindent
named top { 0.0rt }
named ctr { 0.5rt }
named foot { 1.0rt }
{ ctr }
named syntaxgap { 0.35f }
named syntaxbias { 1.0f }
named syntaxradius { 0.3f }
{
###########################################################################
# #
# @Diag symbol #
# #
###########################################################################
export "::" @ShowPoints @ShowTags @ShowDirections @CatchTags @Transform
@Node @ANode @BNode @CNode
@Box @CurveBox @ShadowBox @Square @Diamond @Polygon
@Isosceles @Ellipse @Circle
@ArrowHead @SolidArrowHead @OpenArrowHead @HalfOpenArrowHead
@SolidCurvedArrowHead @OpenCurvedArrowHead @HalfOpenCurvedArrowHead
@CircleArrowHead @BoxArrowHead
@Link
@Line @DoubleLine @Arrow @DoubleArrow @Curve @CurveArrow
@ACurve @ACurveArrow @CCurve @CCurveArrow
@Bezier @BezierArrow
@HVLine @HVArrow @VHLine @VHArrow
@HVCurve @HVCurveArrow @VHCurve @VHCurveArrow
@LVRLine @LVRArrow @RVLLine @RVLArrow
@LVRCurve @LVRCurveArrow @RVLCurve @RVLCurveArrow
@DWrapLine @DWrapArrow @UWrapLine @UWrapArrow
@DWrapCurve @DWrapCurveArrow @UWrapCurve @UWrapCurveArrow
@Tree @HTree
@StartRight @StartUp @StartLeft @StartDown
@StartRightRight @StartRightDown
@Skip @XCell @ACell @BCell @CCell
@Sequence @Select @Optional @OptionalDiverted @Diverted
@Loop @LoopOpposite @Repeat @RepeatOpposite @RepeatDiverted
def @Diag
named save { save }
named maxlabels { maxlabels }
named title { title }
named titleformat
left @Title
right @Body
{ @Title titleformat @Body }
#######################################################################
# #
# @Node options of @Diag #
# #
#######################################################################
import @Geometry named outline
named margin {}
named shadow {}
named sides {}
named angle {}
{ outline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named margin { margin }
import @Geometry named shadow { shadow }
import @Geometry named sides { sides }
import @Geometry named angle { angle }
named translate { translate }
named nodetag { }
named outlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ outlinestyle }
import @Geometry named outlinedashlength{ outlinedashlength }
import @Geometry named outlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ outlinewidth }
named paint { paint }
named font { font }
named break { break }
named format right @Body { format @Body }
named valign { valign }
named vsize { vsize }
named vindent { vindent }
named vstrut
named no { 0.0f }
named yes { 1.0f }
{ vstrut }
named vmargin { vmargin }
named topmargin { topmargin }
named footmargin { footmargin }
named halign { halign }
named hsize { hsize }
named hindent { hindent }
named hstrut
named no { 0.0f }
named yes { 1.0f }
{ hstrut }
named hmargin { hmargin }
named leftmargin { leftmargin }
named rightmargin { rightmargin }
#######################################################################
# #
# @ANode options of @Diag #
# #
#######################################################################
import @Geometry named aoutline
named margin {}
named shadow {}
named sides {}
named angle {}
{ aoutline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named amargin { amargin }
import @Geometry named ashadow { ashadow }
import @Geometry named asides { asides }
import @Geometry named aangle { aangle }
named atranslate { atranslate }
named anodetag { }
named aoutlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ aoutlinestyle }
import @Geometry named aoutlinedashlength{ aoutlinedashlength }
import @Geometry named aoutlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ aoutlinewidth }
named apaint { apaint }
named afont { afont }
named abreak { abreak }
named aformat right @Body { aformat @Body }
named avalign { avalign }
named avsize { avsize }
named avindent { avindent }
named avstrut
named no { 0.0f }
named yes { 1.0f }
{ avstrut }
named avmargin { avmargin }
named atopmargin { atopmargin }
named afootmargin { afootmargin }
named ahalign { ahalign }
named ahsize { ahsize }
named ahindent { ahindent }
named ahstrut
named no { 0.0f }
named yes { 1.0f }
{ ahstrut }
named ahmargin { ahmargin }
named aleftmargin { aleftmargin }
named arightmargin { arightmargin }
#######################################################################
# #
# @BNode options of @Diag #
# #
#######################################################################
import @Geometry named boutline
named margin {}
named shadow {}
named sides {}
named angle {}
{ boutline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named bmargin { bmargin }
import @Geometry named bshadow { bshadow }
import @Geometry named bsides { bsides }
import @Geometry named bangle { bangle }
named btranslate { btranslate }
named bnodetag { }
named boutlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ boutlinestyle }
import @Geometry named boutlinedashlength{ boutlinedashlength }
import @Geometry named boutlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ boutlinewidth }
named bpaint { bpaint }
named bfont { bfont }
named bbreak { bbreak }
named bformat right @Body { bformat @Body }
named bvalign { bvalign }
named bvsize { bvsize }
named bvindent { bvindent }
named bvstrut
named no { 0.0f }
named yes { 1.0f }
{ bvstrut }
named bvmargin { bvmargin }
named btopmargin { btopmargin }
named bfootmargin { bfootmargin }
named bhalign { bhalign }
named bhsize { bhsize }
named bhindent { bhindent }
named bhstrut
named no { 0.0f }
named yes { 1.0f }
{ bhstrut }
named bhmargin { bhmargin }
named bleftmargin { bleftmargin }
named brightmargin { brightmargin }
#######################################################################
# #
# @CNode options of @Diag #
# #
#######################################################################
import @Geometry named coutline
named margin {}
named shadow {}
named sides {}
named angle {}
{ coutline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named cmargin { cmargin }
import @Geometry named cshadow { cshadow }
import @Geometry named csides { csides }
import @Geometry named cangle { cangle }
named ctranslate { ctranslate }
named cnodetag { }
named coutlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ coutlinestyle }
import @Geometry named coutlinedashlength{ coutlinedashlength }
import @Geometry named coutlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ coutlinewidth }
named cpaint { cpaint }
named cfont { cfont }
named cbreak { cbreak }
named cformat right @Body { cformat @Body }
named cvalign { cvalign }
named cvsize { cvsize }
named cvindent { cvindent }
named cvstrut
named no { 0.0f }
named yes { 1.0f }
{ cvstrut }
named cvmargin { cvmargin }
named ctopmargin { ctopmargin }
named cfootmargin { cfootmargin }
named chalign { chalign }
named chsize { chsize }
named chindent { chindent }
named chstrut
named no { 0.0f }
named yes { 1.0f }
{ chstrut }
named chmargin { chmargin }
named cleftmargin { cleftmargin }
named crightmargin { crightmargin }
#######################################################################
# #
# @Link options of @Diag #
# #
#######################################################################
import @Geometry named path
named from {}
named to {}
named bias {}
named fbias {}
named tbias {}
named radius {}
named xindent {}
named zindent {}
named frompt {}
named topt {}
named arrow {}
named arrowlength {}
{ path
from { from }
to { to }
bias { bias }
fbias { fbias }
tbias { tbias }
radius { radius }
xindent { xindent }
zindent { zindent }
frompt { frompt }
topt { topt }
arrow { arrow }
arrowlength { arrowlength }
}
import @Geometry named from { from }
import @Geometry named to { to }
import @Geometry named bias { bias }
import @Geometry named fbias { fbias }
import @Geometry named tbias { tbias }
import @Geometry named radius { radius }
import @Geometry named xindent { xindent }
import @Geometry named zindent { zindent }
import @Geometry named frompt { frompt }
import @Geometry named topt { topt }
named pathstyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ pathstyle }
import @Geometry named pathdashlength { pathdashlength }
import @Geometry named pathwidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ pathwidth }
import @Geometry named pathgap
named thin { 0.08 ft }
named medium { 0.16 ft }
named thick { 0.24 ft }
{ pathgap }
named arrow { arrow }
named arrowstyle { arrowstyle }
named arrowwidth { arrowwidth }
named arrowlength { arrowlength }
named nodelabel { nodelabel }
named nodelabelmargin { nodelabelmargin }
named nodelabelfont { nodelabelfont }
named nodelabelbreak { nodelabelbreak }
named nodelabelformat right @Body { nodelabelformat @Body }
import @Geometry named nodelabelpos { nodelabelpos }
named nodelabelprox { nodelabelprox }
import @Geometry named nodelabelangle { nodelabelangle }
named nodelabelctr { nodelabelctr }
import @Geometry named nodelabeladjust { nodelabeladjust }
named alabel { alabel }
named alabelmargin { alabelmargin }
named alabelfont { alabelfont }
named alabelbreak { alabelbreak }
named alabelformat right @Body { alabelformat @Body }
import @Geometry named alabelpos { alabelpos }
named alabelprox { alabelprox }
import @Geometry named alabelangle { alabelangle }
named alabelctr { alabelctr }
import @Geometry named alabeladjust { alabeladjust }
named blabel { blabel }
named blabelmargin { blabelmargin }
named blabelfont { blabelfont }
named blabelbreak { blabelbreak }
named blabelformat right @Body { blabelformat @Body }
import @Geometry named blabelpos { blabelpos }
named blabelprox { blabelprox }
import @Geometry named blabelangle { blabelangle }
named blabelctr { blabelctr }
import @Geometry named blabeladjust { blabeladjust }
named clabel { clabel }
named clabelmargin { clabelmargin }
named clabelfont { clabelfont }
named clabelbreak { clabelbreak }
named clabelformat right @Body { clabelformat @Body }
import @Geometry named clabelpos { clabelpos }
named clabelprox { clabelprox }
import @Geometry named clabelangle { clabelangle }
named clabelctr { clabelctr }
import @Geometry named clabeladjust { clabeladjust }
named dlabel { dlabel }
named dlabelmargin { dlabelmargin }
named dlabelfont { dlabelfont }
named dlabelbreak { dlabelbreak }
named dlabelformat right @Body { dlabelformat @Body }
import @Geometry named dlabelpos { dlabelpos }
named dlabelprox { dlabelprox }
import @Geometry named dlabelangle { dlabelangle }
named dlabelctr { dlabelctr }
import @Geometry named dlabeladjust { dlabeladjust }
named fromlabel { fromlabel }
named fromlabelmargin { fromlabelmargin }
named fromlabelfont { fromlabelfont }
named fromlabelbreak { fromlabelbreak }
named fromlabelformat right @Body { fromlabelformat @Body }
import @Geometry named fromlabelpos { fromlabelpos }
named fromlabelprox { fromlabelprox }
import @Geometry named fromlabelangle { fromlabelangle }
named fromlabelctr { fromlabelctr }
import @Geometry named fromlabeladjust { fromlabeladjust }
named linklabel { linklabel }
named linklabelmargin { linklabelmargin }
named linklabelfont { linklabelfont }
named linklabelbreak { linklabelbreak }
named linklabelformat right @Body { linklabelformat @Body }
import @Geometry named linklabelpos { linklabelpos }
named linklabelprox { linklabelprox }
import @Geometry named linklabelangle { linklabelangle }
named linklabelctr { linklabelctr }
import @Geometry named linklabeladjust { linklabeladjust }
named xlabel { xlabel }
named xlabelmargin { xlabelmargin }
named xlabelfont { xlabelfont }
named xlabelbreak { xlabelbreak }
named xlabelformat right @Body { xlabelformat @Body }
import @Geometry named xlabelpos { xlabelpos }
named xlabelprox { xlabelprox }
import @Geometry named xlabelangle { xlabelangle }
named xlabelctr { xlabelctr }
import @Geometry named xlabeladjust { xlabeladjust }
named ylabel { ylabel }
named ylabelmargin { ylabelmargin }
named ylabelfont { ylabelfont }
named ylabelbreak { ylabelbreak }
named ylabelformat right @Body { ylabelformat @Body }
import @Geometry named ylabelpos { ylabelpos }
named ylabelprox { ylabelprox }
import @Geometry named ylabelangle { ylabelangle }
named ylabelctr { ylabelctr }
import @Geometry named ylabeladjust { ylabeladjust }
named zlabel { zlabel }
named zlabelmargin { zlabelmargin }
named zlabelfont { zlabelfont }
named zlabelbreak { zlabelbreak }
named zlabelformat right @Body { zlabelformat @Body }
import @Geometry named zlabelpos { zlabelpos }
named zlabelprox { zlabelprox }
import @Geometry named zlabelangle { zlabelangle }
named zlabelctr { zlabelctr }
import @Geometry named zlabeladjust { zlabeladjust }
named tolabel { tolabel }
named tolabelmargin { tolabelmargin }
named tolabelfont { tolabelfont }
named tolabelbreak { tolabelbreak }
named tolabelformat right @Body { tolabelformat @Body }
import @Geometry named tolabelpos { tolabelpos }
named tolabelprox { tolabelprox }
import @Geometry named tolabelangle { tolabelangle }
named tolabelctr { tolabelctr }
import @Geometry named tolabeladjust { tolabeladjust }
#######################################################################
# #
# Tree and syntax diagram options of @Diag #
# #
#######################################################################
named treehsep { treehsep }
named treevsep { treevsep }
named treehindent
named left { 0.0rt }
named ctr { 0.5rt }
named right { 1.0rt }
{ treehindent }
named treevindent
named top { 0.0rt }
named ctr { 0.5rt }
named foot { 1.0rt }
{ treevindent }
named syntaxgap { syntaxgap }
named syntaxbias { syntaxbias }
named syntaxradius { syntaxradius }
body @Body
@Begin
#######################################################################
# #
# Miscellaneous helper definitions #
# #
#######################################################################
# Like @Graphic, but affects the graphics state of right parameter
def @InnerGraphic
left ps
right x
{
@BackEnd @Case {
PostScript @Yield {
{ ps gsave // grestore } @Graphic x
}
PDF @Yield {
{ ps q // Q } @Graphic x
}
}
}
def @BoxLabels right x
{
@BackEnd @Case {
PostScript @Yield {
"[ ldiagbox ] pop" @Graphic x
}
PDF @Yield {}
}
}
def @IfNonEmpty
left x
right y
{
x @Case {
"" @Yield @Null
else @Yield y
}
}
def @Else
precedence 20
associativity right
left x
right y
{
x @Case {
"" @Yield y
else @Yield x
}
}
def @ShowTags
right x
{
@BackEnd @Case {
PostScript @Yield {
{
"() ldiagpushtagdict"
// "ldiagshowtags ldiagpopuptagdict"
} @Graphic x
}
PDF @Yield {}
}
}
def @ShowPoints
right x
{
@BackEnd @Case {
PostScript @Yield {
{
"() ldiagpushtagdict"
// "ldiagshowpoints ldiagpopuptagdict"
} @Graphic x
}
PDF @Yield {}
}
}
def @ShowDirections
right x
{
@BackEnd @Case {
PostScript @Yield {
{ "() ldiagpushtagdict"
// "ldiagshowangles ldiagpopuptagdict" } @Graphic x
}
PDF @Yield {}
}
}
def @ShowMarks right x
{
{ "xmark -0.5 cm moveto xmark ysize 0.5 cm add lineto stroke" } @Graphic x
}
def "::"
precedence 33
associativity right
left name
right x
{
@BackEnd @Case {
PostScript @Yield {
{ "("name") ldiagpushtagdict"
// "ldiagpopuptagdict" } @Graphic x
}
PDF @Yield {}
}
}
def @CatchTags
precedence 33
associativity right
right x
{
@BackEnd @Case {
PostScript @Yield {
{
"() ldiagpushtagdict"
// "ldiagpoptagdict"
}
@Graphic x
}
PDF @Yield {}
}
}
def @ZeroWidth right x
{
@HContract @VContract {
^|0io @HContract @VContract x |0io
}
}
def @ZeroSize right x
{
@HContract @VContract {
^/0io ^|0io @HContract @VContract x |0io /0io
}
}
def @FromArrowLength
left arrow
right arrowlength
{
@BackEnd @Case {
PostScript @Yield {
arrow @Case {
{ no yes forward } @Yield 0
{ back both } @Yield {"("arrowlength") ldiagdecodelength"}
}
}
PDF @Yield {}
}
}
def @ToArrowLength
left arrow
right arrowlength
{
@BackEnd @Case {
PostScript @Yield {
arrow @Case {
{ no back } @Yield 0
{ yes forward both } @Yield {"("arrowlength") ldiagdecodelength"}
}
}
PDF @Yield {}
}
}
def @AddMargins
named mtop {}
named mfoot {}
named mleft {}
named mright {}
right x
{
@HContract @VContract {
^|mleft |mright
^/mtop | x |
/mfoot | |
}
}
def @Transform
precedence 32
import @Geometry named translate
# named to precedence 10 left x right y { x y "ldiagpsub" }
named to precedence 10 left x right y {
@BackEnd @Case {
PostScript @Yield { x y "ldiagpsub" }
PDF @Yield {""}
}
}
{}
import @Geometry named rotate { 0d }
named scale { 1 1 }
right x
{
@BackEnd @Case {
PostScript @Yield {
{ rotate "rotate" scale "scale newpath clip" }
@InnerGraphic
{
@ZeroSize x
}
//
# { rotate "rotate" scale "scale" translate "translate" }
{ translate "translate" rotate "rotate" scale "scale" }
@InnerGraphic
{
@ZeroSize x
}
}
PDF @Yield { # presume that "rotate", "scale" and "translate" are not matrices
{ "__cos("rotate") __sin("rotate") __sub(0, __sin("rotate")) __cos("rotate") 0 0 cm"
"__pick(1, "scale") 0 0 __pick(2, "scale") 0 0 cm n W" }
@InnerGraphic
{
@ZeroSize x
}
//
# { rotate "rotate" scale "scale" translate "translate" }
{ "1 0 0 1 "translate" cm"
"__cos("rotate") __sin("rotate") __sub(0, __sin("rotate")) __cos("rotate") 0 0 cm"
"__pick(1, "scale") 0 0 __pick(2, "scale") 0 0 cm" }
@InnerGraphic
{
@ZeroSize x
}
}
}
}
#######################################################################
# #
# @DoLabel definition for drawing one label #
# #
#######################################################################
def @DoLabel
named which {}
named labeltag { LABEL }
named label {}
named labelmargin {}
named labelfont {}
named labelbreak {}
named labelformat right @Body {}
named labelpos {}
named labelprox {}
named labelangle {}
named labelctr {}
named labeladjust {}
{
import @Geometry
def alignedangle
{
labelpos??"ANGLE" quadcase
0 { labelpos??"ANGLE" }
0-90 { labelpos??"ANGLE" }
90 { labelpos??"ANGLE" }
90-180 { labelpos??"ANGLE" + 180d }
180 { labelpos??"ANGLE" + 180d }
180-270 { labelpos??"ANGLE" + 180d }
270 { labelpos??"ANGLE" + 180d }
270-360 { labelpos??"ANGLE" }
}
import @Geometry
def perpalignedangle
{
labelpos??"ANGLE" quadcase
0 { labelpos??"ANGLE" - 90d }
0-90 { labelpos??"ANGLE" - 90d }
90 { labelpos??"ANGLE" - 90d }
90-180 { labelpos??"ANGLE" - 90d }
180 { labelpos??"ANGLE" + 90d }
180-270 { labelpos??"ANGLE" + 90d }
270 { labelpos??"ANGLE" + 90d }
270-360 { labelpos??"ANGLE" + 90d }
}
import @Geometry
def finalangle
{
labelangle @Case {
"horizontal" @Yield { 0d }
"aligned" @Yield { alignedangle }
"perpendicular" @Yield { perpalignedangle }
"parallel" @Yield { labelpos??"ANGLE" }
"antiparallel" @Yield { labelpos??"ANGLE" + 180d }
else @Yield labelangle
}
}
import @Geometry
def @AlignedAboveProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SW) }
90 { (SW) }
90-180 { (SE) }
180 { (SE) }
180-270 { (SE) }
270 { (SE) }
270-360 { (SW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (SE) }
90-180 { (SW) }
180 { (SW) }
180-270 { (SW) }
270 { (SW) }
270-360 { (SE) }
}
else @Yield (S)
}
}
import @Geometry
def @AlignedBelowProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (NW) }
0-90 { (NW) }
90 { (NW) }
90-180 { (NE) }
180 { (NE) }
180-270 { (NE) }
270 { (NE) }
270-360 { (NW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NE) }
0-90 { (NE) }
90 { (NE) }
90-180 { (NW) }
180 { (NW) }
180-270 { (NW) }
270 { (NW) }
270-360 { (NE) }
}
else @Yield (N)
}
}
import @Geometry
def @AlignedLeftProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SW) }
90 { (SW) }
90-180 { (NE) }
180 { (SE) }
180-270 { (SE) }
270 { (SE) }
270-360 { (NW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (SE) }
90-180 { (NW) }
180 { (SW) }
180-270 { (SW) }
270 { (SW) }
270-360 { (NE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (S) }
0-90 { (S) }
90 { (S) }
90-180 { (N) }
180 { (S) }
180-270 { (S) }
270 { (S) }
270-360 { (N) }
}
}
}
import @Geometry
def @AlignedRightProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (NW) }
90 { (NW) }
90-180 { (SE) }
180 { (SE) }
180-270 { (NE) }
270 { (NE) }
270-360 { (SW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (NE) }
90 { (NE) }
90-180 { (SW) }
180 { (SW) }
180-270 { (NW) }
270 { (NW) }
270-360 { (SE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (S) }
0-90 { (N) }
90 { (N) }
90-180 { (S) }
180 { (S) }
180-270 { (N) }
270 { (N) }
270-360 { (S) }
}
}
}
import @Geometry
def @AlignedInsideProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SW) }
90 { (SW) }
90-180 { (NE) }
180 { (NE) }
180-270 { (NE) }
270 { (NE) }
270-360 { (SW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (SE) }
90-180 { (NW) }
180 { (NW) }
180-270 { (NW) }
270 { (NW) }
270-360 { (SE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (S) }
0-90 { (S) }
90 { (S) }
90-180 { (N) }
180 { (N) }
180-270 { (N) }
270 { (N) }
270-360 { (S) }
}
}
}
import @Geometry
def @AlignedOutsideProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (NW) }
0-90 { (NW) }
90 { (NW) }
90-180 { (SE) }
180 { (SE) }
180-270 { (SE) }
270 { (SE) }
270-360 { (NW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NE) }
0-90 { (NE) }
90 { (NE) }
90-180 { (SW) }
180 { (SW) }
180-270 { (SW) }
270 { (SW) }
270-360 { (NE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (N) }
0-90 { (N) }
90 { (N) }
90-180 { (S) }
180 { (S) }
180-270 { (S) }
270 { (S) }
270-360 { (N) }
}
}
}
import @Geometry
def @PerpendicularAboveProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (SE) }
90-180 { (SW) }
180 { (NE) }
180-270 { (NE) }
270 { (NE) }
270-360 { (NW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NE) }
0-90 { (NE) }
90 { (NE) }
90-180 { (NW) }
180 { (SE) }
180-270 { (SE) }
270 { (SE) }
270-360 { (SW) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (E) }
0-90 { (E) }
90 { (E) }
90-180 { (W) }
180 { (E) }
180-270 { (E) }
270 { (E) }
270-360 { (W) }
}
}
}
import @Geometry
def @PerpendicularBelowProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SW) }
90 { (SW) }
90-180 { (SE) }
180 { (NW) }
180-270 { (NW) }
270 { (NW) }
270-360 { (NE) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NW) }
0-90 { (NW) }
90 { (NW) }
90-180 { (NE) }
180 { (SW) }
180-270 { (SW) }
270 { (SW) }
270-360 { (SE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (W) }
0-90 { (W) }
90 { (W) }
90-180 { (E) }
180 { (W) }
180-270 { (W) }
270 { (W) }
270-360 { (E) }
}
}
}
import @Geometry
def @PerpendicularLeftProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (SE) }
90-180 { (SE) }
180 { (NE) }
180-270 { (NE) }
270 { (NE) }
270-360 { (NE) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NE) }
0-90 { (NE) }
90 { (NE) }
90-180 { (NE) }
180 { (SE) }
180-270 { (SE) }
270 { (SE) }
270-360 { (SE) }
}
else @Yield (E)
}
}
import @Geometry
def @PerpendicularRightProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SW) }
90 { (SW) }
90-180 { (SW) }
180 { (NW) }
180-270 { (NW) }
270 { (NW) }
270-360 { (NW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NW) }
0-90 { (NW) }
90 { (NW) }
90-180 { (NW) }
180 { (SW) }
180-270 { (SW) }
270 { (SW) }
270-360 { (SW) }
}
else @Yield (W)
}
}
import @Geometry
def @PerpendicularInsideProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (SE) }
90-180 { (SE) }
180 { (NW) }
180-270 { (NW) }
270 { (NW) }
270-360 { (NW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NE) }
0-90 { (NE) }
90 { (NE) }
90-180 { (NE) }
180 { (SW) }
180-270 { (SW) }
270 { (SW) }
270-360 { (SW) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (E) }
0-90 { (E) }
90 { (E) }
90-180 { (E) }
180 { (W) }
180-270 { (W) }
270 { (W) }
270-360 { (W) }
}
}
}
import @Geometry
def @PerpendicularOutsideProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SW) }
90 { (SW) }
90-180 { (SW) }
180 { (NE) }
180-270 { (NE) }
270 { (NE) }
270-360 { (NE) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NW) }
0-90 { (NW) }
90 { (NW) }
90-180 { (NW) }
180 { (SE) }
180-270 { (SE) }
270 { (SE) }
270-360 { (SE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (W) }
0-90 { (W) }
90 { (W) }
90-180 { (W) }
180 { (E) }
180-270 { (E) }
270 { (E) }
270-360 { (E) }
}
}
}
import @Geometry
def @OtherAboveProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SE) }
90 { (SW) }
90-180 { (SW) }
180 { (SE) }
180-270 { (SE) }
270 { (NW) }
270-360 { (SW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (NW) }
90-180 { (SW) }
180 { (SW) }
180-270 { (SE) }
270 { (SW) }
270-360 { (SW) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (S) }
0-90 { (SE) }
90 { (W) }
90-180 { (SW) }
180 { (S) }
180-270 { (SE) }
270 { (W) }
270-360 { (SW) }
}
}
}
import @Geometry
def @OtherBelowProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (NW) }
0-90 { (NW) }
90 { (SW) }
90-180 { (NE) }
180 { (NE) }
180-270 { (NW) }
270 { (NW) }
270-360 { (NE) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NE) }
0-90 { (NW) }
90 { (NW) }
90-180 { (NE) }
180 { (NW) }
180-270 { (NW) }
270 { (SW) }
270-360 { (NE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (N) }
0-90 { (NW) }
90 { (W) }
90-180 { (NE) }
180 { (N) }
180-270 { (NW) }
270 { (W) }
270-360 { (NE) }
}
}
}
import @Geometry
def @OtherLeftProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SE) }
90 { (SE) }
90-180 { (NE) }
180 { (SE) }
180-270 { (SE) }
270 { (NE) }
270-360 { (NE) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (NE) }
90-180 { (NE) }
180 { (SW) }
180-270 { (SE) }
270 { (SE) }
270-360 { (NE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (S) }
0-90 { (SE) }
90 { (E) }
90-180 { (NE) }
180 { (S) }
180-270 { (SE) }
270 { (E) }
270-360 { (NE) }
}
}
}
import @Geometry
def @OtherRightProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (NW) }
90 { (SW) }
90-180 { (SW) }
180 { (SE) }
180-270 { (NW) }
270 { (NW) }
270-360 { (SW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (NW) }
90 { (NW) }
90-180 { (SW) }
180 { (SW) }
180-270 { (NW) }
270 { (SW) }
270-360 { (SW) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (S) }
0-90 { (NW) }
90 { (W) }
90-180 { (SW) }
180 { (S) }
180-270 { (NW) }
270 { (W) }
270-360 { (SW) }
}
}
}
import @Geometry
def @OtherInsideProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (SW) }
0-90 { (SE) }
90 { (SE) }
90-180 { (NE) }
180 { (NE) }
180-270 { (NW) }
270 { (NW) }
270-360 { (SW) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (SE) }
0-90 { (SE) }
90 { (NE) }
90-180 { (NE) }
180 { (NW) }
180-270 { (NW) }
270 { (SW) }
270-360 { (SW) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (S) }
0-90 { (SE) }
90 { (E) }
90-180 { (NE) }
180 { (N) }
180-270 { (NW) }
270 { (W) }
270-360 { (SW) }
}
}
}
import @Geometry
def @OtherOutsideProximity
{
which @Case {
{ x f } @Yield { labelpos??ANGLE quadcase
0 { (NW) }
0-90 { (NW) }
90 { (SW) }
90-180 { (SW) }
180 { (SE) }
180-270 { (SE) }
270 { (NE) }
270-360 { (NE) }
}
{ z t } @Yield { labelpos??ANGLE quadcase
0 { (NE) }
0-90 { (NW) }
90 { (NW) }
90-180 { (SW) }
180 { (SW) }
180-270 { (SE) }
270 { (SE) }
270-360 { (NE) }
}
else @Yield { labelpos??ANGLE quadcase
0 { (N) }
0-90 { (NW) }
90 { (W) }
90-180 { (SW) }
180 { (S) }
180-270 { (SE) }
270 { (E) }
270-360 { (NE) }
}
}
}
import @Geometry
def @AboveProximity
{
labelangle @Case {
"aligned" @Yield @AlignedAboveProximity
"perpendicular" @Yield @PerpendicularAboveProximity
else @Yield @OtherAboveProximity
}
}
import @Geometry
def @BelowProximity
{
labelangle @Case {
"aligned" @Yield @AlignedBelowProximity
"perpendicular" @Yield @PerpendicularBelowProximity
else @Yield @OtherBelowProximity
}
}
import @Geometry
def @LeftProximity
{
labelangle @Case {
"aligned" @Yield @AlignedLeftProximity
"perpendicular" @Yield @PerpendicularLeftProximity
else @Yield @OtherLeftProximity
}
}
import @Geometry
def @RightProximity
{
labelangle @Case {
"aligned" @Yield @AlignedRightProximity
"perpendicular" @Yield @PerpendicularRightProximity
else @Yield @OtherRightProximity
}
}
import @Geometry
def @InsideProximity
{
labelangle @Case {
"aligned" @Yield @AlignedInsideProximity
"perpendicular" @Yield @PerpendicularInsideProximity
else @Yield @OtherInsideProximity
}
}
import @Geometry
def @OutsideProximity
{
labelangle @Case {
"aligned" @Yield @AlignedOutsideProximity
"perpendicular" @Yield @PerpendicularOutsideProximity
else @Yield @OtherOutsideProximity
}
}
import @Geometry
def proximity
{
labelprox @Case {
above @Yield @AboveProximity
below @Yield @BelowProximity
left @Yield @LeftProximity
right @Yield @RightProximity
inside @Yield @InsideProximity
outside @Yield @OutsideProximity
else @Yield { "("labelprox")" }
}
}
import @Geometry
def dorotate
left point
right angle
{
{ {0 0} distance point } atangle { {0 0} angleto point + angle }
}
import @Geometry
def translation
{
labelctr @Case {
{ no No } @Yield {
labelpos -- labeltag?!?proximity
}
{ yes Yes } @Yield {
#P0 := labelpos
#P1 := labeltag?!?proximity -- P0
#P2 := labeltag??CTR -- P0
#TH := labelpos??ANGLE
#P1A := P1 dorotate { 0 - TH }
#P2A := P2 dorotate { 0 - TH }
#PRA := { 0 - xcoord P2A 0 - ycoord P1A }
#PRA dorotate TH ++ P0
XP1 := labeltag?!?proximity
XP2 := labeltag??CTR
XANG := labelpos??ANGLE
XTH := XANG - 90d - { XP1 angleto XP2 }
XDIST := { XP1 distance XP2 } * sin XTH
labelpos -- XP1 ++ XDIST atangle XANG
}
}
}
@CatchTags @ZeroSize @Transform
translate { translation ++ labeladjust }
rotate { finalangle }
scale { 1 1 }
labeltag:: @BoxLabels @CatchTags @AddMargins
mtop { labelmargin }
mfoot { labelmargin }
mleft { labelmargin }
mright { labelmargin }
labelfont @Font labelbreak @Break labelformat label
}
#######################################################################
# #
# @Node #
# #
#######################################################################
def @Node
import @Geometry named translate
named to precedence 10 left x right y {
@BackEnd @Case {
PostScript @Yield { x y "ldiagpsub" }
PDF @Yield {""}
}
}
{}
import @Geometry named rotate { 0d }
import @Geometry named outline
named margin {}
named shadow {}
named sides {}
named angle {}
{ outline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named margin { margin }
import @Geometry named shadow { shadow }
import @Geometry named sides { sides }
import @Geometry named angle { angle }
named nodetag { nodetag }
named outlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ outlinestyle }
import @Geometry named outlinedashlength { outlinedashlength}
import @Geometry named outlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ outlinewidth }
named paint { paint }
named font { font }
named break { break }
named format right @Body { format @Body }
named valign { valign }
named vsize { vsize }
named vindent { vindent }
named vstrut
named no { 0.0f }
named yes { 1.0f }
{ vstrut }
named vmargin { vmargin }
named topmargin { topmargin }
named footmargin { footmargin }
named halign { halign }
named hsize { hsize }
named hindent { hindent }
named hstrut
named no { 0.0f }
named yes { 1.0f }
{ hstrut }
named hmargin { hmargin }
named leftmargin { leftmargin }
named rightmargin { rightmargin }
named nodelabel { nodelabel }
named nodelabelmargin { nodelabelmargin }
named nodelabelfont { nodelabelfont }
named nodelabelbreak { nodelabelbreak }
named nodelabelformat right @Body { nodelabelformat @Body }
import @Geometry named nodelabelpos { nodelabelpos }
named nodelabelprox { nodelabelprox }
import @Geometry named nodelabelangle { nodelabelangle }
named nodelabelctr { nodelabelctr }
import @Geometry named nodelabeladjust { nodelabeladjust }
named alabel { alabel }
named alabelmargin { alabelmargin }
named alabelfont { alabelfont }
named alabelbreak { alabelbreak }
named alabelformat right @Body { alabelformat @Body }
import @Geometry named alabelpos { alabelpos }
named alabelprox { alabelprox }
import @Geometry named alabelangle { alabelangle }
named alabelctr { alabelctr }
import @Geometry named alabeladjust { alabeladjust }
named blabel { blabel }
named blabelmargin { blabelmargin }
named blabelfont { blabelfont }
named blabelbreak { blabelbreak }
named blabelformat right @Body { blabelformat @Body }
import @Geometry named blabelpos { blabelpos }
named blabelprox { blabelprox }
import @Geometry named blabelangle { blabelangle }
named blabelctr { blabelctr }
import @Geometry named blabeladjust { blabeladjust }
named clabel { clabel }
named clabelmargin { clabelmargin }
named clabelfont { clabelfont }
named clabelbreak { clabelbreak }
named clabelformat right @Body { clabelformat @Body }
import @Geometry named clabelpos { clabelpos }
named clabelprox { clabelprox }
import @Geometry named clabelangle { clabelangle }
named clabelctr { clabelctr }
import @Geometry named clabeladjust { clabeladjust }
named dlabel { dlabel }
named dlabelmargin { dlabelmargin }
named dlabelfont { dlabelfont }
named dlabelbreak { dlabelbreak }
named dlabelformat right @Body { dlabelformat @Body }
import @Geometry named dlabelpos { dlabelpos }
named dlabelprox { dlabelprox }
import @Geometry named dlabelangle { dlabelangle }
named dlabelctr { dlabelctr }
import @Geometry named dlabeladjust { dlabeladjust }
right @Body
{
def @LabelPos
left x
right y
{
nodelabelpos @Case {
x @Yield y
else @Yield ""
}
}
def @If
left cond
right x
{
cond @Case {
{ yes Yes } @Yield x
else @Yield ""
}
}
def @Strut right x
{
def vs { 0.5w @VShift { vstrut @High } }
def hs { hstrut @Wide }
@HContract @VContract {
@HContract @VContract x | vs / hs |
}
}
def @Indent right x
{
x @Case {
{ top left } @Yield 0.0rt
{ ctr } @Yield 0.5rt
{ foot right } @Yield 1.0rt
{ mctr } @Yield 0.5bx
else @Yield x
}
}
def @VSize right x
{
vsize @Case {
"" @Yield x
else @Yield { vsize @High { /{@Indent vindent} x / } }
}
}
def @HSize right x
{
hsize @Case {
"" @Yield x
else @Yield { hsize @Wide { |{@Indent hindent} x | } }
}
}
def @Align right x
{
x @Case {
{ top left } @Yield 0.0w
{ ctr } @Yield 0.5w
{ foot right } @Yield 1.0w
{ mark } @Yield "+0i"
else @Yield x
}
}
def @ALabel
{
@DoLabel
which { "a" }
label { alabel @Else nodelabel }
labelmargin { alabelmargin @Else nodelabelmargin }
labelfont { alabelfont @Else nodelabelfont }
labelbreak { alabelbreak @Else nodelabelbreak }
labelformat { alabelformat @Body @Else nodelabelformat @Body}
labelpos { alabelpos @Else nodelabelpos }
labelprox { alabelprox @Else nodelabelprox }
labelangle { alabelangle @Else nodelabelangle }
labelctr { alabelctr @Else nodelabelctr }
labeladjust { alabeladjust @Else nodelabeladjust }
}
def @BLabel
{
@DoLabel
which { "b" }
label { blabel @Else nodelabel }
labelmargin { blabelmargin @Else nodelabelmargin }
labelfont { blabelfont @Else nodelabelfont }
labelbreak { blabelbreak @Else nodelabelbreak }
labelformat { blabelformat @Body @Else nodelabelformat @Body}
labelpos { blabelpos @Else nodelabelpos }
labelprox { blabelprox @Else nodelabelprox }
labelangle { blabelangle @Else nodelabelangle }
labelctr { blabelctr @Else nodelabelctr }
labeladjust { blabeladjust @Else nodelabeladjust }
}
def @CLabel
{
@DoLabel
which { "c" }
label { clabel @Else nodelabel }
labelmargin { clabelmargin @Else nodelabelmargin }
labelfont { clabelfont @Else nodelabelfont }
labelbreak { clabelbreak @Else nodelabelbreak }
labelformat { clabelformat @Body @Else nodelabelformat @Body}
labelpos { clabelpos @Else nodelabelpos }
labelprox { clabelprox @Else nodelabelprox }
labelangle { clabelangle @Else nodelabelangle }
labelctr { clabelctr @Else nodelabelctr }
labeladjust { clabeladjust @Else nodelabeladjust }
}
def @DLabel
{
@DoLabel
which { "d" }
label { dlabel @Else nodelabel }
labelmargin { dlabelmargin @Else nodelabelmargin }
labelfont { dlabelfont @Else nodelabelfont }
labelbreak { dlabelbreak @Else nodelabelbreak }
labelformat { dlabelformat @Body @Else nodelabelformat @Body}
labelpos { dlabelpos @Else nodelabelpos }
labelprox { dlabelprox @Else nodelabelprox }
labelangle { dlabelangle @Else nodelabelangle }
labelctr { dlabelctr @Else nodelabelctr }
labeladjust { dlabeladjust @Else nodelabeladjust }
}
import @Geometry
def @OutLine
{
@BackEnd @Case {
PostScript @Yield {
outline @Case {
box @Yield { "ldiagbox" }
curvebox @Yield { "("margin") ldiagcurvebox" }
shadowbox @Yield { shadow "ldiagshadow ldiagbox" }
square @Yield { "ldiagsquare" }
diamond @Yield { "ldiagdiamond" }
polygon @Yield { sides angle "ldiagpolygon" }
isosceles @Yield { "ldiagisosceles" }
ellipse @Yield { "ldiagellipse" }
circle @Yield { "ldiagcircle" }
else @Yield {
outline
margin { "("margin") ldiagdecodelength" }
shadow { shadow }
sides { sides }
angle { angle }
}
}
}
PDF @Yield {}
}
}
def @Value
{
@BackEnd @Case {
PostScript @Yield {
@HContract @VContract
{
{
"ldiagnodebegin [" @OutLine "]"
outlinedashlength "[" outlinestyle "]"
outlinewidth "/ldiag"paint "ldiagnodeend"
"(IN) ldiagpushtagdict"
//
"ldiagpopuptagdict"
}
@Graphic
{
{@Align valign} @VShift {@Align halign} @HShift
@AddMargins
mtop { topmargin @Else vmargin @Else margin }
mfoot { footmargin @Else vmargin @Else margin }
mleft { leftmargin @Else hmargin @Else margin }
mright { rightmargin @Else hmargin @Else margin }
@HSize @VSize @HContract @VContract
font @Font break @Break format @Strut @Body
}
/ {alabel @Else nodelabel} @IfNonEmpty @ALabel
/ {blabel @Else nodelabel} @IfNonEmpty @BLabel
/ {clabel @Else nodelabel} @IfNonEmpty @CLabel
/ {dlabel @Else nodelabel} @IfNonEmpty @DLabel
}
}
PDF @Yield {}
}
}
def @TValue
{
nodetag @Case {
"" @Yield @Value
else @Yield { nodetag:: @Value }
}
}
translate @Case {
"" @Yield @TValue
else @Yield {
@Null & # so that preceding space gets chewed up
@Transform translate { translate } rotate { rotate } @TValue
}
}
}
#######################################################################
# #
# @ANode #
# #
#######################################################################
def @ANode
import @Geometry named translate
named to precedence 10 left x right y {
@BackEnd @Case {
PostScript @Yield { x y "ldiagpsub" }
PDF @Yield {""}
}
}
{}
import @Geometry named rotate { 0d }
import @Geometry named outline
named margin {}
named shadow {}
named sides {}
named angle {}
{ aoutline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named margin { amargin }
import @Geometry named shadow { ashadow }
import @Geometry named sides { asides }
import @Geometry named angle { aangle }
named nodetag { anodetag }
named outlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ aoutlinestyle }
import @Geometry named outlinedashlength { aoutlinedashlength}
import @Geometry named outlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ aoutlinewidth }
named paint { apaint }
named font { afont }
named break { abreak }
named format right @Body { aformat @Body }
named valign { avalign }
named vsize { avsize }
named vindent { avindent }
named vstrut
named no { 0.0f }
named yes { 1.0f }
{ avstrut }
named vmargin { avmargin }
named topmargin { atopmargin }
named footmargin { afootmargin }
named halign { ahalign }
named hsize { ahsize }
named hindent { ahindent }
named hstrut
named no { 0.0f }
named yes { 1.0f }
{ ahstrut }
named hmargin { ahmargin }
named leftmargin { aleftmargin }
named rightmargin { arightmargin }
named nodelabel { anodelabel }
named nodelabelmargin { anodelabelmargin }
named nodelabelfont { anodelabelfont }
named nodelabelbreak { anodelabelbreak }
named nodelabelformat right @Body { anodelabelformat @Body }
import @Geometry named nodelabelpos { anodelabelpos }
named nodelabelprox { anodelabelprox }
import @Geometry named nodelabelangle { anodelabelangle }
named nodelabelctr { anodelabelctr }
import @Geometry named nodelabeladjust { anodelabeladjust }
named alabel { aalabel }
named alabelmargin { aalabelmargin }
named alabelfont { aalabelfont }
named alabelbreak { aalabelbreak }
named alabelformat right @Body { aalabelformat @Body }
import @Geometry named alabelpos { aalabelpos }
named alabelprox { aalabelprox }
import @Geometry named alabelangle { aalabelangle }
named alabelctr { aalabelctr }
import @Geometry named alabeladjust { aalabeladjust }
named blabel { ablabel }
named blabelmargin { ablabelmargin }
named blabelfont { ablabelfont }
named blabelbreak { ablabelbreak }
named blabelformat right @Body { ablabelformat @Body }
import @Geometry named blabelpos { ablabelpos }
named blabelprox { ablabelprox }
import @Geometry named blabelangle { ablabelangle }
named blabelctr { ablabelctr }
import @Geometry named blabeladjust { ablabeladjust }
named clabel { aclabel }
named clabelmargin { aclabelmargin }
named clabelfont { aclabelfont }
named clabelbreak { aclabelbreak }
named clabelformat right @Body { aclabelformat @Body }
import @Geometry named clabelpos { aclabelpos }
named clabelprox { aclabelprox }
import @Geometry named clabelangle { aclabelangle }
named clabelctr { aclabelctr }
import @Geometry named clabeladjust { aclabeladjust }
named dlabel { adlabel }
named dlabelmargin { adlabelmargin }
named dlabelfont { adlabelfont }
named dlabelbreak { adlabelbreak }
named dlabelformat right @Body { adlabelformat @Body }
import @Geometry named dlabelpos { adlabelpos }
named dlabelprox { adlabelprox }
import @Geometry named dlabelangle { adlabelangle }
named dlabelctr { adlabelctr }
import @Geometry named dlabeladjust { adlabeladjust }
right @Body
{
def @LabelPos
left x
right y
{
nodelabelpos @Case {
x @Yield y
else @Yield ""
}
}
def @If
left cond
right x
{
cond @Case {
{ yes Yes } @Yield x
else @Yield ""
}
}
def @Strut right x
{
def vs { 0.5w @VShift { vstrut @High } }
def hs { hstrut @Wide }
@HContract @VContract {
@HContract @VContract x | vs / hs |
}
}
def @Indent right x
{
x @Case {
{ top left } @Yield 0.0rt
{ ctr } @Yield 0.5rt
{ foot right } @Yield 1.0rt
{ mctr } @Yield 0.5bx
else @Yield x
}
}
def @VSize right x
{
vsize @Case {
"" @Yield x
else @Yield { vsize @High { /{@Indent vindent} x / } }
}
}
def @HSize right x
{
hsize @Case {
"" @Yield x
else @Yield { hsize @Wide { |{@Indent hindent} x | } }
}
}
def @Align right x
{
x @Case {
{ top left } @Yield 0.0w
{ ctr } @Yield 0.5w
{ foot right } @Yield 1.0w
{ mark } @Yield "+0i"
else @Yield x
}
}
def @ALabel
{
@DoLabel
which { "a" }
label { alabel @Else nodelabel }
labelmargin { alabelmargin @Else nodelabelmargin }
labelfont { alabelfont @Else nodelabelfont }
labelbreak { alabelbreak @Else nodelabelbreak }
labelformat { alabelformat @Body @Else nodelabelformat @Body}
labelpos { alabelpos @Else nodelabelpos }
labelprox { alabelprox @Else nodelabelprox }
labelangle { alabelangle @Else nodelabelangle }
labelctr { alabelctr @Else nodelabelctr }
labeladjust { alabeladjust @Else nodelabeladjust }
}
def @BLabel
{
@DoLabel
which { "b" }
label { blabel @Else nodelabel }
labelmargin { blabelmargin @Else nodelabelmargin }
labelfont { blabelfont @Else nodelabelfont }
labelbreak { blabelbreak @Else nodelabelbreak }
labelformat { blabelformat @Body @Else nodelabelformat @Body}
labelpos { blabelpos @Else nodelabelpos }
labelprox { blabelprox @Else nodelabelprox }
labelangle { blabelangle @Else nodelabelangle }
labelctr { blabelctr @Else nodelabelctr }
labeladjust { blabeladjust @Else nodelabeladjust }
}
def @CLabel
{
@DoLabel
which { "c" }
label { clabel @Else nodelabel }
labelmargin { clabelmargin @Else nodelabelmargin }
labelfont { clabelfont @Else nodelabelfont }
labelbreak { clabelbreak @Else nodelabelbreak }
labelformat { clabelformat @Body @Else nodelabelformat @Body}
labelpos { clabelpos @Else nodelabelpos }
labelprox { clabelprox @Else nodelabelprox }
labelangle { clabelangle @Else nodelabelangle }
labelctr { clabelctr @Else nodelabelctr }
labeladjust { clabeladjust @Else nodelabeladjust }
}
def @DLabel
{
@DoLabel
which { "d" }
label { dlabel @Else nodelabel }
labelmargin { dlabelmargin @Else nodelabelmargin }
labelfont { dlabelfont @Else nodelabelfont }
labelbreak { dlabelbreak @Else nodelabelbreak }
labelformat { dlabelformat @Body @Else nodelabelformat @Body}
labelpos { dlabelpos @Else nodelabelpos }
labelprox { dlabelprox @Else nodelabelprox }
labelangle { dlabelangle @Else nodelabelangle }
labelctr { dlabelctr @Else nodelabelctr }
labeladjust { dlabeladjust @Else nodelabeladjust }
}
import @Geometry
def @OutLine
{
@BackEnd @Case {
PostScript @Yield {
outline @Case {
box @Yield { "ldiagbox" }
curvebox @Yield { "("margin") ldiagcurvebox" }
shadowbox @Yield { shadow "ldiagshadow ldiagbox" }
square @Yield { "ldiagsquare" }
diamond @Yield { "ldiagdiamond" }
polygon @Yield { sides angle "ldiagpolygon" }
isosceles @Yield { "ldiagisosceles" }
ellipse @Yield { "ldiagellipse" }
circle @Yield { "ldiagcircle" }
else @Yield {
outline
margin { "("margin") ldiagdecodelength" }
shadow { shadow }
sides { sides }
angle { angle }
}
}
}
PDF @Yield {}
}
}
def @Value
{
@BackEnd @Case {
PostScript @Yield {
@HContract @VContract
{
{
"ldiagnodebegin [" @OutLine "]"
outlinedashlength "[" outlinestyle "]"
outlinewidth "/ldiag"paint "ldiagnodeend"
"(IN) ldiagpushtagdict"
//
"ldiagpopuptagdict"
}
@Graphic
{
{@Align valign} @VShift {@Align halign} @HShift
@AddMargins
mtop { topmargin @Else vmargin @Else margin }
mfoot { footmargin @Else vmargin @Else margin }
mleft { leftmargin @Else hmargin @Else margin }
mright { rightmargin @Else hmargin @Else margin }
@HSize @VSize @HContract @VContract
font @Font break @Break format @Strut @Body
}
/ {alabel @Else nodelabel} @IfNonEmpty @ALabel
/ {blabel @Else nodelabel} @IfNonEmpty @BLabel
/ {clabel @Else nodelabel} @IfNonEmpty @CLabel
/ {dlabel @Else nodelabel} @IfNonEmpty @DLabel
}
}
PDF @Yield {}
}
}
def @TValue
{
nodetag @Case {
"" @Yield @Value
else @Yield { nodetag:: @Value }
}
}
translate @Case {
"" @Yield @TValue
else @Yield {
@Null & # so that preceding space gets chewed up
@Transform translate { translate } rotate { rotate } @TValue
}
}
}
#######################################################################
# #
# @BNode #
# #
#######################################################################
def @BNode
import @Geometry named translate
named to precedence 10 left x right y {
@BackEnd @Case {
PostScript @Yield { x y "ldiagpsub" }
PDF @Yield {""}
}
}
{}
import @Geometry named rotate { 0d }
import @Geometry named outline
named margin {}
named shadow {}
named sides {}
named angle {}
{ boutline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named margin { bmargin }
import @Geometry named shadow { bshadow }
import @Geometry named sides { bsides }
import @Geometry named angle { bangle }
named nodetag { bnodetag }
named outlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ boutlinestyle }
import @Geometry named outlinedashlength { boutlinedashlength}
import @Geometry named outlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ boutlinewidth }
named paint { bpaint }
named font { bfont }
named break { bbreak }
named format right @Body { bformat @Body }
named valign { bvalign }
named vsize { bvsize }
named vindent { bvindent }
named vstrut
named no { 0.0f }
named yes { 1.0f }
{ bvstrut }
named vmargin { bvmargin }
named topmargin { btopmargin }
named footmargin { bfootmargin }
named halign { bhalign }
named hsize { bhsize }
named hindent { bhindent }
named hstrut
named no { 0.0f }
named yes { 1.0f }
{ bhstrut }
named hmargin { bhmargin }
named leftmargin { bleftmargin }
named rightmargin { brightmargin }
named nodelabel { bnodelabel }
named nodelabelmargin { bnodelabelmargin }
named nodelabelfont { bnodelabelfont }
named nodelabelbreak { bnodelabelbreak }
named nodelabelformat right @Body { bnodelabelformat @Body }
import @Geometry named nodelabelpos { bnodelabelpos }
named nodelabelprox { bnodelabelprox }
import @Geometry named nodelabelangle { bnodelabelangle }
named nodelabelctr { bnodelabelctr }
import @Geometry named nodelabeladjust { bnodelabeladjust }
named alabel { balabel }
named alabelmargin { balabelmargin }
named alabelfont { balabelfont }
named alabelbreak { balabelbreak }
named alabelformat right @Body { balabelformat @Body }
import @Geometry named alabelpos { balabelpos }
named alabelprox { balabelprox }
import @Geometry named alabelangle { balabelangle }
named alabelctr { balabelctr }
import @Geometry named alabeladjust { balabeladjust }
named blabel { bblabel }
named blabelmargin { bblabelmargin }
named blabelfont { bblabelfont }
named blabelbreak { bblabelbreak }
named blabelformat right @Body { bblabelformat @Body }
import @Geometry named blabelpos { bblabelpos }
named blabelprox { bblabelprox }
import @Geometry named blabelangle { bblabelangle }
named blabelctr { bblabelctr }
import @Geometry named blabeladjust { bblabeladjust }
named clabel { bclabel }
named clabelmargin { bclabelmargin }
named clabelfont { bclabelfont }
named clabelbreak { bclabelbreak }
named clabelformat right @Body { bclabelformat @Body }
import @Geometry named clabelpos { bclabelpos }
named clabelprox { bclabelprox }
import @Geometry named clabelangle { bclabelangle }
named clabelctr { bclabelctr }
import @Geometry named clabeladjust { bclabeladjust }
named dlabel { bdlabel }
named dlabelmargin { bdlabelmargin }
named dlabelfont { bdlabelfont }
named dlabelbreak { bdlabelbreak }
named dlabelformat right @Body { bdlabelformat @Body }
import @Geometry named dlabelpos { bdlabelpos }
named dlabelprox { bdlabelprox }
import @Geometry named dlabelangle { bdlabelangle }
named dlabelctr { bdlabelctr }
import @Geometry named dlabeladjust { bdlabeladjust }
right @Body
{
def @LabelPos
left x
right y
{
nodelabelpos @Case {
x @Yield y
else @Yield ""
}
}
def @If
left cond
right x
{
cond @Case {
{ yes Yes } @Yield x
else @Yield ""
}
}
def @Strut right x
{
def vs { 0.5w @VShift { vstrut @High } }
def hs { hstrut @Wide }
@HContract @VContract {
@HContract @VContract x | vs / hs |
}
}
def @Indent right x
{
x @Case {
{ top left } @Yield 0.0rt
{ ctr } @Yield 0.5rt
{ foot right } @Yield 1.0rt
{ mctr } @Yield 0.5bx
else @Yield x
}
}
def @VSize right x
{
vsize @Case {
"" @Yield x
else @Yield { vsize @High { /{@Indent vindent} x / } }
}
}
def @HSize right x
{
hsize @Case {
"" @Yield x
else @Yield { hsize @Wide { |{@Indent hindent} x | } }
}
}
def @Align right x
{
x @Case {
{ top left } @Yield 0.0w
{ ctr } @Yield 0.5w
{ foot right } @Yield 1.0w
{ mark } @Yield "+0i"
else @Yield x
}
}
def @ALabel
{
@DoLabel
which { "a" }
label { alabel @Else nodelabel }
labelmargin { alabelmargin @Else nodelabelmargin }
labelfont { alabelfont @Else nodelabelfont }
labelbreak { alabelbreak @Else nodelabelbreak }
labelformat { alabelformat @Body @Else nodelabelformat @Body}
labelpos { alabelpos @Else nodelabelpos }
labelprox { alabelprox @Else nodelabelprox }
labelangle { alabelangle @Else nodelabelangle }
labelctr { alabelctr @Else nodelabelctr }
labeladjust { alabeladjust @Else nodelabeladjust }
}
def @BLabel
{
@DoLabel
which { "b" }
label { blabel @Else nodelabel }
labelmargin { blabelmargin @Else nodelabelmargin }
labelfont { blabelfont @Else nodelabelfont }
labelbreak { blabelbreak @Else nodelabelbreak }
labelformat { blabelformat @Body @Else nodelabelformat @Body}
labelpos { blabelpos @Else nodelabelpos }
labelprox { blabelprox @Else nodelabelprox }
labelangle { blabelangle @Else nodelabelangle }
labelctr { blabelctr @Else nodelabelctr }
labeladjust { blabeladjust @Else nodelabeladjust }
}
def @CLabel
{
@DoLabel
which { "c" }
label { clabel @Else nodelabel }
labelmargin { clabelmargin @Else nodelabelmargin }
labelfont { clabelfont @Else nodelabelfont }
labelbreak { clabelbreak @Else nodelabelbreak }
labelformat { clabelformat @Body @Else nodelabelformat @Body}
labelpos { clabelpos @Else nodelabelpos }
labelprox { clabelprox @Else nodelabelprox }
labelangle { clabelangle @Else nodelabelangle }
labelctr { clabelctr @Else nodelabelctr }
labeladjust { clabeladjust @Else nodelabeladjust }
}
def @DLabel
{
@DoLabel
which { "d" }
label { dlabel @Else nodelabel }
labelmargin { dlabelmargin @Else nodelabelmargin }
labelfont { dlabelfont @Else nodelabelfont }
labelbreak { dlabelbreak @Else nodelabelbreak }
labelformat { dlabelformat @Body @Else nodelabelformat @Body}
labelpos { dlabelpos @Else nodelabelpos }
labelprox { dlabelprox @Else nodelabelprox }
labelangle { dlabelangle @Else nodelabelangle }
labelctr { dlabelctr @Else nodelabelctr }
labeladjust { dlabeladjust @Else nodelabeladjust }
}
import @Geometry
def @OutLine
{
@BackEnd @Case {
PostScript @Yield {
outline @Case {
box @Yield { "ldiagbox" }
curvebox @Yield { "("margin") ldiagcurvebox" }
shadowbox @Yield { shadow "ldiagshadow ldiagbox" }
square @Yield { "ldiagsquare" }
diamond @Yield { "ldiagdiamond" }
polygon @Yield { sides angle "ldiagpolygon" }
isosceles @Yield { "ldiagisosceles" }
ellipse @Yield { "ldiagellipse" }
circle @Yield { "ldiagcircle" }
else @Yield {
outline
margin { "("margin") ldiagdecodelength" }
shadow { shadow }
sides { sides }
angle { angle }
}
}
}
PDF @Yield {}
}
}
def @Value
{
@BackEnd @Case {
PostScript @Yield {
@HContract @VContract
{
{
"ldiagnodebegin [" @OutLine "]"
outlinedashlength "[" outlinestyle "]"
outlinewidth "/ldiag"paint "ldiagnodeend"
"(IN) ldiagpushtagdict"
//
"ldiagpopuptagdict"
}
@Graphic
{
{@Align valign} @VShift {@Align halign} @HShift
@AddMargins
mtop { topmargin @Else vmargin @Else margin }
mfoot { footmargin @Else vmargin @Else margin }
mleft { leftmargin @Else hmargin @Else margin }
mright { rightmargin @Else hmargin @Else margin }
@HSize @VSize @HContract @VContract
font @Font break @Break format @Strut @Body
}
/ {alabel @Else nodelabel} @IfNonEmpty @ALabel
/ {blabel @Else nodelabel} @IfNonEmpty @BLabel
/ {clabel @Else nodelabel} @IfNonEmpty @CLabel
/ {dlabel @Else nodelabel} @IfNonEmpty @DLabel
}
}
PDF @Yield {}
}
}
def @TValue
{
nodetag @Case {
"" @Yield @Value
else @Yield { nodetag:: @Value }
}
}
translate @Case {
"" @Yield @TValue
else @Yield {
@Null & # so that preceding space gets chewed up
@Transform translate { translate } rotate { rotate } @TValue
}
}
}
#######################################################################
# #
# @CNode #
# #
#######################################################################
def @CNode
import @Geometry named translate
named to precedence 10 left x right y {
@BackEnd @Case {
PostScript @Yield { x y "ldiagpsub" }
PDF @Yield {""}
}
}
{}
import @Geometry named rotate { 0d }
import @Geometry named outline
named margin {}
named shadow {}
named sides {}
named angle {}
{ coutline
margin { margin }
shadow { shadow }
sides { sides }
angle { angle }
}
named margin { cmargin }
import @Geometry named shadow { cshadow }
import @Geometry named sides { csides }
import @Geometry named angle { cangle }
named nodetag { cnodetag }
named outlinestyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ coutlinestyle }
import @Geometry named outlinedashlength { coutlinedashlength}
import @Geometry named outlinewidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ coutlinewidth }
named paint { cpaint }
named font { cfont }
named break { cbreak }
named format right @Body { cformat @Body }
named valign { cvalign }
named vsize { cvsize }
named vindent { cvindent }
named vstrut
named no { 0.0f }
named yes { 1.0f }
{ cvstrut }
named vmargin { cvmargin }
named topmargin { ctopmargin }
named footmargin { cfootmargin }
named halign { chalign }
named hsize { chsize }
named hindent { chindent }
named hstrut
named no { 0.0f }
named yes { 1.0f }
{ chstrut }
named hmargin { chmargin }
named leftmargin { cleftmargin }
named rightmargin { crightmargin }
named nodelabel { cnodelabel }
named nodelabelmargin { cnodelabelmargin }
named nodelabelfont { cnodelabelfont }
named nodelabelbreak { cnodelabelbreak }
named nodelabelformat right @Body { cnodelabelformat @Body }
import @Geometry named nodelabelpos { cnodelabelpos }
named nodelabelprox { cnodelabelprox }
import @Geometry named nodelabelangle { cnodelabelangle }
named nodelabelctr { cnodelabelctr }
import @Geometry named nodelabeladjust { cnodelabeladjust }
named alabel { calabel }
named alabelmargin { calabelmargin }
named alabelfont { calabelfont }
named alabelbreak { calabelbreak }
named alabelformat right @Body { calabelformat @Body }
import @Geometry named alabelpos { calabelpos }
named alabelprox { calabelprox }
import @Geometry named alabelangle { calabelangle }
named alabelctr { calabelctr }
import @Geometry named alabeladjust { calabeladjust }
named blabel { cblabel }
named blabelmargin { cblabelmargin }
named blabelfont { cblabelfont }
named blabelbreak { cblabelbreak }
named blabelformat right @Body { cblabelformat @Body }
import @Geometry named blabelpos { cblabelpos }
named blabelprox { cblabelprox }
import @Geometry named blabelangle { cblabelangle }
named blabelctr { cblabelctr }
import @Geometry named blabeladjust { cblabeladjust }
named clabel { cclabel }
named clabelmargin { cclabelmargin }
named clabelfont { cclabelfont }
named clabelbreak { cclabelbreak }
named clabelformat right @Body { cclabelformat @Body }
import @Geometry named clabelpos { cclabelpos }
named clabelprox { cclabelprox }
import @Geometry named clabelangle { cclabelangle }
named clabelctr { cclabelctr }
import @Geometry named clabeladjust { cclabeladjust }
named dlabel { cdlabel }
named dlabelmargin { cdlabelmargin }
named dlabelfont { cdlabelfont }
named dlabelbreak { cdlabelbreak }
named dlabelformat right @Body { cdlabelformat @Body }
import @Geometry named dlabelpos { cdlabelpos }
named dlabelprox { cdlabelprox }
import @Geometry named dlabelangle { cdlabelangle }
named dlabelctr { cdlabelctr }
import @Geometry named dlabeladjust { cdlabeladjust }
right @Body
{
def @LabelPos
left x
right y
{
nodelabelpos @Case {
x @Yield y
else @Yield ""
}
}
def @If
left cond
right x
{
cond @Case {
{ yes Yes } @Yield x
else @Yield ""
}
}
def @Strut right x
{
def vs { 0.5w @VShift { vstrut @High } }
def hs { hstrut @Wide }
@HContract @VContract {
@HContract @VContract x | vs / hs |
}
}
def @Indent right x
{
x @Case {
{ top left } @Yield 0.0rt
{ ctr } @Yield 0.5rt
{ foot right } @Yield 1.0rt
{ mctr } @Yield 0.5bx
else @Yield x
}
}
def @VSize right x
{
vsize @Case {
"" @Yield x
else @Yield { vsize @High { /{@Indent vindent} x / } }
}
}
def @HSize right x
{
hsize @Case {
"" @Yield x
else @Yield { hsize @Wide { |{@Indent hindent} x | } }
}
}
def @Align right x
{
x @Case {
{ top left } @Yield 0.0w
{ ctr } @Yield 0.5w
{ foot right } @Yield 1.0w
{ mark } @Yield "+0i"
else @Yield x
}
}
def @ALabel
{
@DoLabel
which { "a" }
label { alabel @Else nodelabel }
labelmargin { alabelmargin @Else nodelabelmargin }
labelfont { alabelfont @Else nodelabelfont }
labelbreak { alabelbreak @Else nodelabelbreak }
labelformat { alabelformat @Body @Else nodelabelformat @Body}
labelpos { alabelpos @Else nodelabelpos }
labelprox { alabelprox @Else nodelabelprox }
labelangle { alabelangle @Else nodelabelangle }
labelctr { alabelctr @Else nodelabelctr }
labeladjust { alabeladjust @Else nodelabeladjust }
}
def @BLabel
{
@DoLabel
which { "b" }
label { blabel @Else nodelabel }
labelmargin { blabelmargin @Else nodelabelmargin }
labelfont { blabelfont @Else nodelabelfont }
labelbreak { blabelbreak @Else nodelabelbreak }
labelformat { blabelformat @Body @Else nodelabelformat @Body}
labelpos { blabelpos @Else nodelabelpos }
labelprox { blabelprox @Else nodelabelprox }
labelangle { blabelangle @Else nodelabelangle }
labelctr { blabelctr @Else nodelabelctr }
labeladjust { blabeladjust @Else nodelabeladjust }
}
def @CLabel
{
@DoLabel
which { "c" }
label { clabel @Else nodelabel }
labelmargin { clabelmargin @Else nodelabelmargin }
labelfont { clabelfont @Else nodelabelfont }
labelbreak { clabelbreak @Else nodelabelbreak }
labelformat { clabelformat @Body @Else nodelabelformat @Body}
labelpos { clabelpos @Else nodelabelpos }
labelprox { clabelprox @Else nodelabelprox }
labelangle { clabelangle @Else nodelabelangle }
labelctr { clabelctr @Else nodelabelctr }
labeladjust { clabeladjust @Else nodelabeladjust }
}
def @DLabel
{
@DoLabel
which { "d" }
label { dlabel @Else nodelabel }
labelmargin { dlabelmargin @Else nodelabelmargin }
labelfont { dlabelfont @Else nodelabelfont }
labelbreak { dlabelbreak @Else nodelabelbreak }
labelformat { dlabelformat @Body @Else nodelabelformat @Body}
labelpos { dlabelpos @Else nodelabelpos }
labelprox { dlabelprox @Else nodelabelprox }
labelangle { dlabelangle @Else nodelabelangle }
labelctr { dlabelctr @Else nodelabelctr }
labeladjust { dlabeladjust @Else nodelabeladjust }
}
import @Geometry
def @OutLine
{
@BackEnd @Case {
PostScript @Yield {
outline @Case {
box @Yield { "ldiagbox" }
curvebox @Yield { "("margin") ldiagcurvebox" }
shadowbox @Yield { shadow "ldiagshadow ldiagbox" }
square @Yield { "ldiagsquare" }
diamond @Yield { "ldiagdiamond" }
polygon @Yield { sides angle "ldiagpolygon" }
isosceles @Yield { "ldiagisosceles" }
ellipse @Yield { "ldiagellipse" }
circle @Yield { "ldiagcircle" }
else @Yield {
outline
margin { "("margin") ldiagdecodelength" }
shadow { shadow }
sides { sides }
angle { angle }
}
}
}
PDF @Yield {}
}
}
def @Value
{
@BackEnd @Case {
PostScript @Yield {
@HContract @VContract
{
{
"ldiagnodebegin [" @OutLine "]"
outlinedashlength "[" outlinestyle "]"
outlinewidth "/ldiag"paint "ldiagnodeend"
"(IN) ldiagpushtagdict"
//
"ldiagpopuptagdict"
}
@Graphic
{
{@Align valign} @VShift {@Align halign} @HShift
@AddMargins
mtop { topmargin @Else vmargin @Else margin }
mfoot { footmargin @Else vmargin @Else margin }
mleft { leftmargin @Else hmargin @Else margin }
mright { rightmargin @Else hmargin @Else margin }
@HSize @VSize @HContract @VContract
font @Font break @Break format @Strut @Body
}
/ {alabel @Else nodelabel} @IfNonEmpty @ALabel
/ {blabel @Else nodelabel} @IfNonEmpty @BLabel
/ {clabel @Else nodelabel} @IfNonEmpty @CLabel
/ {dlabel @Else nodelabel} @IfNonEmpty @DLabel
}
}
PDF @Yield {}
}
}
def @TValue
{
nodetag @Case {
"" @Yield @Value
else @Yield { nodetag:: @Value }
}
}
translate @Case {
"" @Yield @TValue
else @Yield {
@Null & # so that preceding space gets chewed up
@Transform translate { translate } rotate { rotate } @TValue
}
}
}
#######################################################################
# #
# @Box, @CurveBox, and other standard node abbreviations #
# #
#######################################################################
macro @@Node { @Node }
macro @Box { @Node outline { box } }
macro @CurveBox { @Node outline { curvebox } }
macro @ShadowBox { @Node outline { shadowbox } }
macro @Square { @Node outline { square } }
macro @Diamond { @Node outline { diamond } }
macro @Polygon { @Node outline { polygon } }
macro @Isosceles { @Node outline { isosceles } }
macro @Ellipse { @Node outline { ellipse } }
macro @Circle { @Node outline { circle } }
#######################################################################
# #
# Arrowheads #
# #
#######################################################################
macro @InsulatedNode {
@Node
topmargin { 0i }
footmargin { 0i }
leftmargin { 0i }
rightmargin { 0i }
alabel {}
blabel {}
clabel {}
dlabel {}
hsize {}
vsize {}
vstrut { no }
hstrut { no }
}
def @SolidArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
paint { nochange }
outlinestyle { noline }
outlinewidth { pathwidth }
outline {
@BackEnd @Case {
PostScript @Yield {
"ldiagsolidarrowhead"
# 0 0 xsize ysize * 0.5 0 ysize
}
PDF @Yield {}
}
}
{
length @Wide width @High
}
}
def @OpenArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
outlinewidth { pathwidth }
outlinestyle { noline }
paint { nochange }
outline {
@BackEnd @Case {
PostScript @Yield {
pathwidth "ldiagopenarrowhead"
# PSW := { 0 0 }
# PNW := { 0 ysize }
# PE := { xsize ysize*0.5 }
# REL := pathwidth atangle { PE angleto PNW + 90d }
# PNA := { 0 ysize*0.5 + pathwidth*0.5 }
# PSA := { 0 ysize*0.5 - pathwidth*0.5 }
# PNI := {
# PNA PNA ++ { xsize 0 }
# PNW ++ REL PE ++ REL ldiaglineintersect
# }
# PSI := PNI -- { 0 pathwidth }
#
# PSW PE PNW PNI PNA PSA PSI PSW
}
PDF @Yield {}
}
}
{
length @Wide width @High
}
}
def @HalfOpenArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
paint { nochange }
outlinestyle { noline }
outlinewidth { pathwidth }
outline {
@BackEnd @Case {
PostScript @Yield {
pathwidth "ldiaghalfopenarrowhead"
# 0 0
# xsize ysize * 0.5
# 0 ysize
# xsize*0.3 ysize*0.5 + pathwidth*0.5
# 0 ysize*0.5 + pathwidth*0.5
# 0 ysize*0.5 - pathwidth*0.5
# xsize*0.3 ysize*0.5 - pathwidth*0.5
# 0 0
}
PDF @Yield {}
}
}
{
length @Wide width @High
}
}
def @SolidCurvedArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
outlinestyle { noline }
paint { nochange }
outlinewidth { pathwidth }
outline {
@BackEnd @Case {
PostScript @Yield {
"ldiagsolidcurvedarrowhead"
# 0 0
# [0 0 xsize ysize * 0.5 "ldiaglinebetween"
# xsize 0 xsize ysize "ldiaglineintersect" clockwise]
# xsize ysize * 0.5
# [xsize ysize * 0.5 0 ysize "ldiaglinebetween"
# xsize 0 xsize ysize "ldiaglineintersect" clockwise]
# 0 ysize
}
PDF @Yield {}
}
}
{
length @Wide width @High
}
}
def @OpenCurvedArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
outlinestyle { noline }
paint { nochange }
outlinewidth { pathwidth }
outline {
@BackEnd @Case {
PostScript @Yield {
pathwidth "ldiagopencurvedarrowhead"
# LR:= { 0 0 xsize ysize * 0.5 "ldiaglinebetween"
# xsize 0 xsize ysize "ldiaglineintersect" }
# UR:= { xsize ysize * 0.5 0 ysize "ldiaglinebetween"
# xsize 0 xsize ysize "ldiaglineintersect" }
# PW2 := pathwidth * 0.5
# UMID := {
# 0 ysize * 0.5 + PW2 xsize ysize * 0.5 + PW2
# {0 ysize} ++ 1f atangle { UR angleto {0 ysize} + 90d }
# { 0 ysize } ldiaglineintersect
# }
# LMID := UMID -- { 0 pathwidth }
# 0 0
# [LR clockwise]
# xsize ysize * 0.5
# [UR clockwise]
# 0 ysize
# UMID
# 0 ysize * 0.5 + PW2
# 0 ysize * 0.5 - PW2
# LMID
# 0 0
}
PDF @Yield {}
}
}
{
length @Wide width @High
}
}
def @HalfOpenCurvedArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
outlinestyle { noline }
paint { nochange }
outlinewidth { pathwidth }
outline {
@BackEnd @Case {
PostScript @Yield {
pathwidth "ldiaghalfopencurvedarrowhead"
# LR:= { 0 0 xsize ysize * 0.5 "ldiaglinebetween"
# xsize 0 xsize ysize "ldiaglineintersect" }
# UR:= { xsize ysize * 0.5 0 ysize "ldiaglinebetween"
# xsize 0 xsize ysize "ldiaglineintersect" }
# BR:= { 0 0 LR 0 ysize UR "ldiaglineintersect" }
# BRAD := { 0 0 } distance BR
# PW2 := pathwidth * 0.5
# XDIST := sqrt { BRAD*BRAD - PW2*PW2 }
# UMID := BR ++ { XDIST PW2 }
# LMID := BR ++ { XDIST 0 - PW2 }
# 0 0
# [LR clockwise]
# xsize ysize * 0.5
# [UR clockwise]
# 0 ysize
# [BR clockwise ]
# UMID
# 0 ysize * 0.5 + PW2
# 0 ysize * 0.5 - PW2
# LMID
# [BR clockwise ]
# 0 0
}
PDF @Yield {}
}
}
{
length @Wide width @High
}
}
def @CircleArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
outlinestyle { noline }
paint { nochange }
outlinewidth { pathwidth }
outline { circle }
{ length @Wide length @High }
}
def @BoxArrowHead
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
@InsulatedNode
outlinestyle { noline }
paint { nochange }
outlinewidth { pathwidth }
outline { box }
{ length @Wide width @High }
}
def @ArrowHead
named style { arrowstyle }
named width { arrowwidth }
named length { arrowlength }
named pathwidth { pathwidth }
{
style @Case {
solid @Yield @SolidArrowHead
width { width } length { length }
pathwidth { pathwidth }
halfopen @Yield @HalfOpenArrowHead
width { width } length { length }
pathwidth { pathwidth }
open @Yield @OpenArrowHead
width { width } length { length }
pathwidth { pathwidth }
curvedsolid @Yield @SolidCurvedArrowHead
width { width } length { length }
pathwidth { pathwidth }
curvedhalfopen @Yield @HalfOpenCurvedArrowHead
width { width } length { length }
pathwidth { pathwidth }
curvedopen @Yield @OpenCurvedArrowHead
width { width } length { length }
pathwidth { pathwidth }
circle @Yield @CircleArrowHead
width { width } length { length }
pathwidth { pathwidth }
box @Yield @BoxArrowHead
width { width } length { length }
pathwidth { pathwidth }
}
}
#######################################################################
# #
# @Link #
# #
#######################################################################
def @Link
import @Geometry named path
named from {}
named to {}
named bias {}
named fbias {}
named tbias {}
named radius {}
named xindent {}
named zindent {}
named frompt {}
named topt {}
named arrow {}
named arrowlength {}
{ path
from { from }
to { to }
bias { bias }
fbias { fbias }
tbias { tbias }
radius { radius }
xindent { xindent }
zindent { zindent }
frompt { frompt }
topt { topt }
arrow { arrow }
arrowlength { arrowlength }
}
import @Geometry named from { from }
import @Geometry named to { to }
import @Geometry named bias { bias }
import @Geometry named fbias { fbias }
import @Geometry named tbias { tbias }
import @Geometry named radius { radius }
import @Geometry named xindent { xindent }
import @Geometry named zindent { zindent }
import @Geometry named frompt { frompt }
import @Geometry named topt { topt }
named pathstyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ pathstyle }
import @Geometry named pathdashlength { pathdashlength }
import @Geometry named pathwidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ pathwidth }
import @Geometry named pathgap
named thin { 0.08 ft }
named medium { 0.16 ft }
named thick { 0.24 ft }
{ pathgap }
named arrow { arrow }
named arrowstyle { arrowstyle }
named arrowwidth { arrowwidth }
named arrowlength { arrowlength }
named linklabel { linklabel }
named linklabelmargin { linklabelmargin }
named linklabelfont { linklabelfont }
named linklabelbreak { linklabelbreak }
named linklabelformat right @Body { linklabelformat @Body }
import @Geometry named linklabelpos { linklabelpos }
named linklabelprox { linklabelprox }
import @Geometry named linklabelangle { linklabelangle }
named linklabelctr { linklabelctr }
import @Geometry named linklabeladjust { linklabeladjust }
named xlabel { xlabel }
named xlabelmargin { xlabelmargin }
named xlabelfont { xlabelfont }
named xlabelbreak { xlabelbreak }
named xlabelformat right @Body { xlabelformat @Body }
import @Geometry named xlabelpos { xlabelpos }
named xlabelprox { xlabelprox }
import @Geometry named xlabelangle { xlabelangle }
named xlabelctr { xlabelctr }
import @Geometry named xlabeladjust { xlabeladjust }
named ylabel { ylabel }
named ylabelmargin { ylabelmargin }
named ylabelfont { ylabelfont }
named ylabelbreak { ylabelbreak }
named ylabelformat right @Body { ylabelformat @Body }
import @Geometry named ylabelpos { ylabelpos }
named ylabelprox { ylabelprox }
import @Geometry named ylabelangle { ylabelangle }
named ylabelctr { ylabelctr }
import @Geometry named ylabeladjust { ylabeladjust }
named zlabel { zlabel }
named zlabelmargin { zlabelmargin }
named zlabelfont { zlabelfont }
named zlabelbreak { zlabelbreak }
named zlabelformat right @Body { zlabelformat @Body }
import @Geometry named zlabelpos { zlabelpos }
named zlabelprox { zlabelprox }
import @Geometry named zlabelangle { zlabelangle }
named zlabelctr { zlabelctr }
import @Geometry named zlabeladjust { zlabeladjust }
named fromlabel { fromlabel }
named fromlabelmargin { fromlabelmargin }
named fromlabelfont { fromlabelfont }
named fromlabelbreak { fromlabelbreak }
named fromlabelformat right @Body { fromlabelformat @Body }
import @Geometry named fromlabelpos { fromlabelpos }
named fromlabelprox { fromlabelprox }
import @Geometry named fromlabelangle { fromlabelangle }
named fromlabelctr { fromlabelctr }
import @Geometry named fromlabeladjust { fromlabeladjust }
named tolabel { tolabel }
named tolabelmargin { tolabelmargin }
named tolabelfont { tolabelfont }
named tolabelbreak { tolabelbreak }
named tolabelformat right @Body { tolabelformat @Body }
import @Geometry named tolabelpos { tolabelpos }
named tolabelprox { tolabelprox }
import @Geometry named tolabelangle { tolabelangle }
named tolabelctr { tolabelctr }
import @Geometry named tolabeladjust{ tolabeladjust }
{
def @XLabel
{
@DoLabel
which { "x" }
label { xlabel @Else linklabel }
labelmargin { xlabelmargin @Else linklabelmargin }
labelfont { xlabelfont @Else linklabelfont }
labelbreak { xlabelbreak @Else linklabelbreak }
labelformat { xlabelformat @Body @Else linklabelformat @Body}
labelpos { xlabelpos @Else linklabelpos }
labelprox { xlabelprox @Else linklabelprox }
labelangle { xlabelangle @Else linklabelangle }
labelctr { xlabelctr @Else linklabelctr }
labeladjust { xlabeladjust @Else linklabeladjust }
}
def @YLabel
{
@DoLabel
which { "y" }
label { ylabel @Else linklabel }
labelmargin { ylabelmargin @Else linklabelmargin }
labelfont { ylabelfont @Else linklabelfont }
labelbreak { ylabelbreak @Else linklabelbreak }
labelformat { ylabelformat @Body @Else linklabelformat @Body}
labelpos { ylabelpos @Else linklabelpos }
labelprox { ylabelprox @Else linklabelprox }
labelangle { ylabelangle @Else linklabelangle }
labelctr { ylabelctr @Else linklabelctr }
labeladjust { ylabeladjust @Else linklabeladjust }
}
def @ZLabel
{
@DoLabel
which { "z" }
label { zlabel @Else linklabel }
labelmargin { zlabelmargin @Else linklabelmargin }
labelfont { zlabelfont @Else linklabelfont }
labelbreak { zlabelbreak @Else linklabelbreak }
labelformat { zlabelformat @Body @Else linklabelformat @Body}
labelpos { zlabelpos @Else linklabelpos }
labelprox { zlabelprox @Else linklabelprox }
labelangle { zlabelangle @Else linklabelangle }
labelctr { zlabelctr @Else linklabelctr }
labeladjust { zlabeladjust @Else linklabeladjust }
}
def @FromArrow
{
arrow @Case {
{ back both } @Yield {
@ArrowHead
style { arrowstyle }
width { arrowwidth }
length { arrowlength }
pathwidth { pathwidth }
}
else @Yield ""
}
}
def @ToArrow
{
arrow @Case {
{ yes forward both } @Yield {
@ArrowHead
style { arrowstyle }
width { arrowwidth }
length { arrowlength }
pathwidth { pathwidth }
}
else @Yield ""
}
}
import @Geometry
def @LinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent "ldiaglinepath"
# FROM :< {from??CTR angleto to??CTR}
# FROM :: from boundaryatangle FROM@ANGLE
# ++ {arrow @FromArrowLength arrowlength}atangle FROM@ANGLE
# TO :< FROM@ANGLE
# TO :: to boundaryatangle { TO@ANGLE - 180d }
# ++ {arrow @ToArrowLength arrowlength} atangle {TO@ANGLE - 180d}
#
# LMID :: FROM ** 0.5 ++ TO ** 0.5
# LMID :< FROM@ANGLE
# XINDENT := xindent min { FROM distance LMID }
# LFROM :: FROM ++ XINDENT atangle FROM@ANGLE
# LFROM :< FROM@ANGLE
# ZINDENT := zindent min { TO distance LMID }
# LTO :: TO -- ZINDENT atangle FROM@ANGLE
# LTO :< FROM@ANGLE
#
# if cond { direct }
# then { FROM TO }
# else { FROM LFROM LMID LTO TO }
}
PDF @Yield {}
}
}
import @Geometry
def @DoubleLinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent pathgap "ldiagdoublelinepath"
# FROM :< {from??CTR angleto to??CTR}
# FROM :: from boundaryatangle FROM@ANGLE
# ++ {arrow @FromArrowLength arrowlength}atangle FROM@ANGLE
# TO :< FROM@ANGLE
# TO :: to boundaryatangle { TO@ANGLE - 180d }
# ++ {arrow @ToArrowLength arrowlength} atangle {TO@ANGLE - 180d}
#
# LMID :: FROM ** 0.5 ++ TO ** 0.5
# LMID :< FROM@ANGLE
# XINDENT := xindent min { FROM distance LMID }
# LFROM :: FROM ++ XINDENT atangle FROM@ANGLE
# LFROM :< FROM@ANGLE
# ZINDENT := zindent min { TO distance LMID }
# LTO :: TO -- ZINDENT atangle FROM@ANGLE
# LTO :< FROM@ANGLE
#
# if cond { direct }
# then { FROM TO }
# else { FROM LFROM LMID LTO TO }
}
PDF @Yield {}
}
}
import @Geometry
def @ACurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias "ldiagacurvepath"
# #B1 := bias max 0.02f
# #B2 := { from??CTR distance to??CTR } * 0.5
# #BIAS := B1 min B2
# BIAS := bias max 0.02f
# XMID := from??CTR ** 0.5 ++ to??CTR ** 0.5
# XTOP := XMID ++ BIAS atangle {from??CTR angleto to??CTR - 90d}
# CTR := { from??CTR XTOP ldiaglinebetween
# to??CTR XTOP ldiaglinebetween ldiaglineintersect }
# FROM :: aabout
# circum { from }
# extra { arrow @FromArrowLength arrowlength }
# centre { CTR }
# FROM :< if cond { from??CTR distance FROM > 0 }
# then { from??CTR angleto FROM }
# else { CTR angleto FROM + 90d }
# TO :: cabout
# circum { to }
# extra { arrow @ToArrowLength arrowlength }
# centre { CTR }
# TO :< if cond { TO distance to??CTR > 0 }
# then { TO angleto to??CTR }
# else { CTR angleto TO + 90d }
#
# RADIUS := CTR distance FROM
# LMID :: CTR ++ RADIUS atangle {
# CTR angleto FROM +
# { {360d + {CTR angleto TO} - {CTR angleto FROM}} mod 360 } / 2
# }
# LMID :< CTR angleto LMID + 90d
#
# XINDENT := xindent min { FROM distance LMID }
# LFROM :: CTR ++ RADIUS atangle {
# CTR angleto { FROM ++ XINDENT atangle FROM@ANGLE } }
# LFROM :< CTR angleto LFROM + 90d
# ZINDENT := zindent min { TO distance LMID }
# LTO :: CTR ++ RADIUS atangle {
# CTR angleto { TO ++ ZINDENT atangle {TO@ANGLE+180d}}}
# LTO :< CTR angleto LTO + 90d
#
# if cond { direct }
# then { FROM [CTR] TO }
# else { FROM [CTR] LFROM [CTR] LMID [CTR] LTO [CTR] TO }
}
PDF @Yield {}
}
}
import @Geometry
def @CCurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias "ldiagccurvepath"
# #B1 := bias max 0.02f
# #B2 := { from??CTR distance to??CTR } * 0.5
# #BIAS := B1 min B2
# BIAS := bias max 0.02f
# XMID := from??CTR ** 0.5 ++ to??CTR ** 0.5
# XTOP := XMID ++ BIAS atangle {from??CTR angleto to??CTR + 90d}
# CTR := { from??CTR XTOP ldiaglinebetween
# to??CTR XTOP ldiaglinebetween ldiaglineintersect }
# FROM :: cabout
# circum { from }
# extra { arrow @FromArrowLength arrowlength }
# centre { CTR }
# FROM :< if cond { from??CTR distance FROM > 0 }
# then { from??CTR angleto FROM }
# else { CTR angleto FROM - 90d }
# TO :: aabout
# circum { to }
# extra { arrow @ToArrowLength arrowlength }
# centre { CTR }
# TO :< if cond { TO distance to??CTR > 0 }
# then { TO angleto to??CTR }
# else { CTR angleto TO - 90d }
#
# RADIUS := CTR distance FROM
# LMID :: CTR ++ RADIUS atangle {
# CTR angleto TO +
# { {360d + {CTR angleto FROM} - {CTR angleto TO} } mod 360 } / 2
# }
# LMID :< CTR angleto LMID - 90d
#
# XINDENT := xindent min { FROM distance LMID }
# LFROM :: CTR ++ RADIUS atangle {
# CTR angleto { FROM ++ XINDENT atangle FROM@ANGLE } }
# LFROM :< CTR angleto LFROM - 90d
# ZINDENT := zindent min { TO distance LMID }
# LTO :: CTR ++ RADIUS atangle {
# CTR angleto { TO ++ ZINDENT atangle {TO@ANGLE+180d}}}
# LTO :< CTR angleto LTO - 90d
#
# if cond { direct }
# then { FROM [CTR clockwise] TO }
# else { FROM [CTR clockwise] LFROM [CTR clockwise]
# LMID [CTR clockwise] LTO [CTR clockwise] TO }
}
PDF @Yield {}
}
}
import @Geometry
def @BezierPath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent [ frompt ] [ topt ] "ldiagbezierpath"
# FROM :< from??CTR angleto frompt
# FROM :: from boundaryatangle FROM@ANGLE
# ++ {arrow @FromArrowLength arrowlength} atangle FROM@ANGLE
# TO :< topt angleto to??CTR
# TO :: to boundaryatangle { TO@ANGLE + 180d }
# ++ {arrow @ToArrowLength arrowlength} atangle { TO@ANGLE + 180d }
# LFROM :: FROM ++ { xindent atangle FROM@ANGLE }
# LFROM :< FROM@ANGLE
# LTO :: TO ++ zindent atangle { TO@ANGLE + 180d }
# LTO :< TO@ANGLE
# LMID :: { FROM ++ TO ++ frompt ++ topt } ** 0.25
# FROM [frompt topt] TO
}
PDF @Yield {}
}
}
import @Geometry
def @VHLinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent "ldiagvhlinepath"
# CTR := { {xcoord from??CTR} {ycoord to??CTR} }
# FANG := from??CTR angleto CTR
# TANG := to??CTR angleto CTR
# FROM :: from boundaryatangle FANG
# ++ {arrow @FromArrowLength arrowlength} atangle FANG
# FROM :< FANG
# TO :: to boundaryatangle TANG
# ++ {arrow @ToArrowLength arrowlength} atangle TANG
# TO :< TANG + 180d
# FDIST := FROM distance CTR
# TDIST := TO distance CTR
# XINDENT := xindent min FDIST
# ZINDENT := zindent min TDIST
# LFROM :: FROM ++ XINDENT atangle FANG
# LFROM :< FROM@ANGLE
# LTO :: TO ++ ZINDENT atangle TANG
# LTO :< TO@ANGLE
# LMID :: CTR
# LMID :< {1f atangle {FANG + 180d}} angleto
# {1f atangle {TANG + 180d}}
# FROM LFROM LMID LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @VHCurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent radius "ldiagvhcurvepath"
# CTR := { {xcoord from??CTR} {ycoord to??CTR} }
# FANG := from??CTR angleto CTR
# TANG := to??CTR angleto CTR
# FROM :: from boundaryatangle FANG
# ++ {arrow @FromArrowLength arrowlength} atangle FANG
# FROM :< FANG
# TO :: to boundaryatangle TANG
# ++ {arrow @ToArrowLength arrowlength} atangle TANG
# TO :< TANG + 180d
# FDIST := FROM distance CTR
# TDIST := TO distance CTR
# RADIUS := radius min FDIST min TDIST
# XINDENT := xindent min { FDIST - RADIUS }
# ZINDENT := zindent min { TDIST - RADIUS }
# LFROM :: FROM ++ XINDENT atangle FANG
# LFROM :< FROM@ANGLE
# LTO :: TO ++ ZINDENT atangle TANG
# LTO :< TO@ANGLE
# FCTR := CTR ++ RADIUS atangle { FROM@ANGLE + 180d }
# TCTR := CTR ++ RADIUS atangle { TO@ANGLE }
# XCTR := CTR ++ RADIUS atangle { FROM@ANGLE + 180d }
# ++ RADIUS atangle { TO@ANGLE }
# LMID :: XCTR ++ RADIUS atangle { XCTR angleto CTR }
# LMID :< FCTR angleto TCTR
# FROM LFROM FCTR
# { FCTR angleto TCTR } quadcase
# 0 { }
# 0-90 { [XCTR clockwise] }
# 90 { }
# 90-180 { [XCTR] }
# 180 { }
# 180-270 { [XCTR clockwise] }
# 270 { }
# 270-360 { [XCTR] }
# TCTR LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @HVLinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent "ldiaghvlinepath"
# CTR := { {xcoord to??CTR} {ycoord from??CTR} }
# FANG := from??CTR angleto CTR
# TANG := to??CTR angleto CTR
# FROM :: from boundaryatangle FANG
# ++ {arrow @FromArrowLength arrowlength} atangle FANG
# FROM :< FANG
# TO :: to boundaryatangle TANG
# ++ {arrow @ToArrowLength arrowlength} atangle TANG
# TO :< TANG + 180d
# FDIST := FROM distance CTR
# TDIST := TO distance CTR
# XINDENT := xindent min FDIST
# ZINDENT := zindent min TDIST
# LFROM :: FROM ++ XINDENT atangle FANG
# LFROM :< FROM@ANGLE
# LTO :: TO ++ ZINDENT atangle TANG
# LTO :< TO@ANGLE
# LMID :: CTR
# LMID :< {1f atangle {FANG + 180d}} angleto
# {1f atangle {TANG + 180d}}
# FROM LFROM LMID LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @HVCurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent radius "ldiaghvcurvepath"
# CTR := { {xcoord to??CTR} {ycoord from??CTR} }
# FANG := from??CTR angleto CTR
# TANG := to??CTR angleto CTR
# FROM :: from boundaryatangle FANG
# ++ {arrow @FromArrowLength arrowlength} atangle FANG
# FROM :< FANG
# TO :: to boundaryatangle TANG
# ++ {arrow @ToArrowLength arrowlength} atangle TANG
# TO :< TANG + 180d
# FDIST := FROM distance CTR
# TDIST := TO distance CTR
# RADIUS := radius min FDIST min TDIST
# XINDENT := xindent min { FDIST - RADIUS }
# ZINDENT := zindent min { TDIST - RADIUS }
# LFROM :: FROM ++ XINDENT atangle FANG
# LFROM :< FROM@ANGLE
# LTO :: TO ++ ZINDENT atangle TANG
# LTO :< TO@ANGLE
# FCTR := CTR ++ RADIUS atangle { FROM@ANGLE + 180d }
# TCTR := CTR ++ RADIUS atangle { TO@ANGLE }
# XCTR := CTR ++ RADIUS atangle { FROM@ANGLE + 180d }
# ++ RADIUS atangle { TO@ANGLE }
# LMID :: XCTR ++ RADIUS atangle { XCTR angleto CTR }
# LMID :< FCTR angleto TCTR
# FROM LFROM FCTR
# { FCTR angleto TCTR } quadcase
# 0 { }
# 0-90 { [XCTR] }
# 90 { }
# 90-180 { [XCTR clockwise] }
# 180 { }
# 180-270 { [XCTR] }
# 270 { }
# 270-360 { [XCTR clockwise] }
# TCTR LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @LVRLinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias "ldiaglvrlinepath"
# FROM :: from boundaryatangle 180d
# ++ {arrow @FromArrowLength arrowlength} atangle 180d
# FROM :< 180d
# TO :: to boundaryatangle 180d
# ++ {arrow @ToArrowLength arrowlength} atangle 180d
# TO :< 0d
# XLEFT := {{xcoord FROM} min {xcoord TO}} - bias
# P1 :: { XLEFT ycoord FROM }
# P2 :: { XLEFT ycoord TO }
# VERT := P1 angleto P2
# P1 :< P1 angleto {P1++{1f atangle 180d}++{1f atangle VERT}}
# P2 :< P2 angleto {P2++{1f atangle 0d} ++{1f atangle VERT}}
# LMID :: P1 ** 0.5 ++ P2 ** 0.5
# LMID :< VERT
# XINDENT := xindent min {FROM distance P1}
# ZINDENT := zindent min {P2 distance TO}
# LFROM :: FROM -- { XINDENT 0 }
# LFROM :< 180d
# LTO :: TO -- { ZINDENT 0 }
# LTO :< 0d
# FROM LFROM P1 LMID P2 LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @LVRCurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias radius "ldiaglvrcurvepath"
# FROM :: from boundaryatangle 180d
# ++ {arrow @FromArrowLength arrowlength} atangle 180d
# FROM :< 180d
# TO :: to boundaryatangle 180d
# ++ {arrow @ToArrowLength arrowlength} atangle 180d
# TO :< 0d
# XLEFT := {{xcoord FROM} min {xcoord TO}} - bias
# XP1 := { XLEFT ycoord FROM }
# XP2 := { XLEFT ycoord TO }
# VERT := XP1 angleto XP2
# LMID :: XP1 ** 0.5 ++ XP2 ** 0.5
# LMID :< VERT
# XINDENT := xindent min {FROM distance XP1}
# ZINDENT := zindent min {XP2 distance TO}
# LFROM :: FROM -- { XINDENT 0 }
# LFROM :< 180d
# LTO :: TO -- { ZINDENT 0 }
# LTO :< 0d
# RADIUS := radius min { { XP1 distance XP2 } / 2 }
# XP1PRE := XP1 ++ { RADIUS atangle 0d }
# XP1POST := XP1 ++ { RADIUS atangle VERT }
# XP1CTR := XP1PRE ++ { RADIUS atangle VERT }
# P1 :: XP1CTR ++ { RADIUS atangle { XP1CTR angleto XP1 } }
# P1 :< XP1PRE angleto XP1POST
# XP2PRE := XP2 -- { RADIUS atangle VERT }
# XP2POST := XP2 ++ { RADIUS atangle 0d }
# XP2CTR := XP2PRE ++ { RADIUS atangle 0d }
# P2 :: XP2CTR ++ { RADIUS atangle { XP2CTR angleto XP2 } }
# P2 :< XP2PRE angleto XP2POST
# FROM LFROM XP1PRE
# {round VERT} quadcase
# 90 { [XP1CTR clockwise] P1 [XP1CTR clockwise] }
# 270 { [XP1CTR] P1 [XP1CTR] }
# XP1POST LMID XP2PRE
# {round VERT} quadcase
# 90 { [XP2CTR clockwise] P2 [XP2CTR clockwise] }
# 270 { [XP2CTR] P2 [XP2CTR] }
# XP2POST LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @RVLLinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias "ldiagrvllinepath"
# FROM :: from boundaryatangle 0d
# ++ {arrow @FromArrowLength arrowlength} atangle 0d
# FROM :< 0d
# TO :: to boundaryatangle 0d
# ++ {arrow @ToArrowLength arrowlength} atangle 0d
# TO :< 180d
# XRIGHT := {{xcoord FROM} max {xcoord TO}} + bias
# P1 :: { XRIGHT ycoord FROM }
# P2 :: { XRIGHT ycoord TO }
# VERT := P1 angleto P2
# P1 :< P1 angleto {P1++{1f atangle 0d} ++{1f atangle VERT}}
# P2 :< P2 angleto {P2++{1f atangle 180d}++{1f atangle VERT}}
# LMID :: P1 ** 0.5 ++ P2 ** 0.5
# LMID :< VERT
# XINDENT := xindent min {FROM distance P1}
# ZINDENT := zindent min {P2 distance TO}
# LFROM :: FROM ++ { XINDENT 0 }
# LFROM :< 0d
# LTO :: TO ++ { ZINDENT 0 }
# LTO :< 180d
# FROM LFROM P1 LMID P2 LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @RVLCurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias radius "ldiagrvlcurvepath"
# FROM :: from boundaryatangle 0d
# ++ {arrow @FromArrowLength arrowlength} atangle 0d
# FROM :< 0d
# TO :: to boundaryatangle 0d
# ++ {arrow @ToArrowLength arrowlength} atangle 0d
# TO :< 180d
# XRIGHT := {{xcoord FROM} max {xcoord TO}} + bias
# XP1 := { XRIGHT ycoord FROM }
# XP2 := { XRIGHT ycoord TO }
# VERT := XP1 angleto XP2
# LMID :: XP1 ** 0.5 ++ XP2 ** 0.5
# LMID :< VERT
# XINDENT := xindent min {FROM distance XP1}
# ZINDENT := zindent min {XP2 distance TO}
# LFROM :: FROM ++ { XINDENT 0 }
# LFROM :< 0d
# LTO :: TO ++ { ZINDENT 0 }
# LTO :< 180d
# RADIUS := radius min { { XP1 distance XP2 } * 0.5 }
# XP1PRE := XP1 ++ { RADIUS atangle 180d }
# XP1POST := XP1 ++ { RADIUS atangle VERT }
# XP1CTR := XP1PRE ++ { RADIUS atangle VERT }
# P1 :: XP1CTR ++ { RADIUS atangle { XP1CTR angleto XP1 } }
# P1 :< XP1PRE angleto XP1POST
# XP2PRE := XP2 -- { RADIUS atangle VERT }
# XP2POST := XP2 ++ { RADIUS atangle 180d }
# XP2CTR := XP2PRE ++ { RADIUS atangle 180d }
# P2 :: XP2CTR ++ { RADIUS atangle { XP2CTR angleto XP2 } }
# P2 :< XP2PRE angleto XP2POST
# FROM LFROM XP1PRE
# {round VERT} quadcase
# 90 { [XP1CTR] P1 [XP1CTR] }
# 270 { [XP1CTR clockwise] P1 [XP1CTR clockwise] }
# XP1POST LMID XP2PRE
# {round VERT} quadcase
# 90 { [XP2CTR] P2 [XP2CTR] }
# 270 { [XP2CTR clockwise] P2 [XP2CTR clockwise] }
# XP2POST LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @DWrapLinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias fbias tbias "ldiagdwraplinepath"
# DIRN := if cond { xcoord from??CTR < xcoord to??CTR }
# then { 180d } else { 0d }
# FROM :: from boundaryatangle DIRN
# ++ {arrow @FromArrowLength arrowlength} atangle DIRN
# FROM :< DIRN
# TO :: to boundaryatangle { DIRN + 180d }
# ++ {arrow @ToArrowLength arrowlength} atangle { DIRN + 180d }
# TO :< DIRN
# P1 :: FROM ++ {fbias max 0} atangle DIRN
# P1 :< if cond { DIRN = 180d } then { 225d } else { -45d }
# P4 :: TO ++ {tbias max 0} atangle { DIRN + 180d }
# P4 :< if cond { DIRN = 180d } then { 135d } else { 45d }
# YC := ycoord { from boundaryatangle 270d } min
# ycoord { to boundaryatangle 270d }
# - { bias max 0 }
# P2 :: { xcoord P1 YC }
# P2 :< P4@ANGLE - 180d
# P3 :: { xcoord P4 YC }
# P3 :< P1@ANGLE - 180d
# XINDENT := xindent min { FROM distance P1 }
# LFROM :: FROM ++ XINDENT atangle DIRN
# LFROM :< FROM@ANGLE
# ZINDENT := zindent min { TO distance P4 }
# LTO :: TO ++ ZINDENT atangle { DIRN + 180d }
# LTO :< TO@ANGLE
# LMID :: P2 ** 0.5 ++ P3 ** 0.5
# LMID :< DIRN - 180d
# FROM P1 P2 P3 P4 TO
}
PDF @Yield {}
}
}
import @Geometry
def @DWrapCurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias fbias tbias radius "ldiagdwrapcurvepath"
# DIRN := if cond { xcoord from??CTR < xcoord to??CTR }
# then { 180d } else { 0d }
# CLOCK := if cond { xcoord from??CTR < xcoord to??CTR }
# then { anticlockwise } else { clockwise }
# FROM :: from boundaryatangle DIRN
# ++ {arrow @FromArrowLength arrowlength} atangle DIRN
# FROM :< DIRN
# TO :: to boundaryatangle { DIRN + 180d }
# ++ {arrow @ToArrowLength arrowlength} atangle { DIRN + 180d }
# TO :< DIRN
#
# XP1 := FROM ++ {fbias max 0} atangle DIRN
# XP4 := TO ++ {tbias max 0} atangle { DIRN + 180d }
# YC := ycoord { from boundaryatangle 270d } min
# ycoord { to boundaryatangle 270d }
# - { bias max 0 }
# XP2 := { xcoord XP1 YC }
# XP3 := { xcoord XP4 YC }
#
# RP1 := radius min { XP1 distance FROM } min
# { { XP1 distance XP2 } / 2 }
# XP1PRE := XP1 ++ RP1 atangle { XP1 angleto FROM }
# XP1POST := XP1 ++ RP1 atangle { XP1 angleto XP2 }
# XP1CTR := XP1PRE ++ RP1 atangle { XP1 angleto XP2 }
# P1 :: XP1CTR ++ RP1 atangle { XP1CTR angleto XP1 }
# P1 :< XP1CTR angleto P1 + DIRN - 90d
#
# RP2 := radius min { { XP1 distance XP2 } / 2 }
# min { { XP2 distance XP3 } / 2 }
# XP2PRE := XP2 ++ RP2 atangle { XP2 angleto XP1 }
# XP2POST := XP2 ++ RP2 atangle { XP2 angleto XP3 }
# XP2CTR := XP2PRE ++ RP2 atangle { XP2 angleto XP3 }
# P2 :: XP2CTR ++ RP2 atangle { XP2CTR angleto XP2 }
# P2 :< XP2CTR angleto P2 + DIRN - 90d
#
# RP3 := radius min { { XP2 distance XP3 } / 2 }
# min { { XP3 distance XP4 } / 2 }
# XP3PRE := XP3 ++ RP3 atangle { XP3 angleto XP2 }
# XP3POST := XP3 ++ RP3 atangle { XP3 angleto XP4 }
# XP3CTR := XP3PRE ++ RP3 atangle { XP3 angleto XP4 }
# P3 :: XP3CTR ++ RP3 atangle { XP3CTR angleto XP3 }
# P3 :< XP3CTR angleto P3 + DIRN - 90d
#
# RP4 := radius min { { XP4 distance XP3 } / 2 }
# min { XP4 distance TO }
# XP4PRE := XP4 ++ RP4 atangle { XP4 angleto XP3 }
# XP4POST := XP4 ++ RP4 atangle { XP4 angleto TO }
# XP4CTR := XP4PRE ++ RP4 atangle { XP4 angleto TO }
# P4 :: XP4CTR ++ RP4 atangle { XP4CTR angleto XP4 }
# P4 :< XP4CTR angleto P4 + DIRN - 90d
#
# XINDENT := xindent min { FROM distance XP1PRE }
# LFROM :: FROM ++ XINDENT atangle DIRN
# LFROM :< FROM@ANGLE
#
# LMID :: XP2 ** 0.5 ++ XP3 ** 0.5
# LMID :< DIRN - 180d
#
# ZINDENT := zindent min { TO distance XP4POST }
# LTO :: TO ++ ZINDENT atangle { DIRN + 180d }
# LTO :< TO@ANGLE
#
# FROM LFROM
# XP1PRE [XP1CTR CLOCK] XP1POST
# XP2PRE [XP2CTR CLOCK] XP2POST
# LMID
# XP3PRE [XP3CTR CLOCK] XP3POST
# XP4PRE [XP4CTR CLOCK] XP4POST
# LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @UWrapLinePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias fbias tbias "ldiaguwraplinepath"
# DIRN := if cond { xcoord from??CTR < xcoord to??CTR }
# then { 180d } else { 0d }
# FROM :: from boundaryatangle DIRN
# ++ {arrow @FromArrowLength arrowlength} atangle DIRN
# FROM :< DIRN
# TO :: to boundaryatangle { DIRN + 180d }
# ++ {arrow @ToArrowLength arrowlength} atangle { DIRN + 180d }
# TO :< DIRN
# P1 :: FROM ++ {fbias max 0} atangle DIRN
# P1 :< if cond { DIRN = 180d } then { 135d } else { 45d }
# P4 :: TO ++ {tbias max 0} atangle { DIRN + 180d }
# P4 :< if cond { DIRN = 180d } then { 225d } else { -45d }
# YC := ycoord { from boundaryatangle 90d } max
# ycoord { to boundaryatangle 90d }
# + { bias max 0 }
# P2 :: { xcoord P1 YC }
# P2 :< P4@ANGLE - 180d
# P3 :: { xcoord P4 YC }
# P3 :< P1@ANGLE - 180d
# XINDENT := xindent min { FROM distance P1 }
# LFROM :: FROM ++ XINDENT atangle DIRN
# LFROM :< FROM@ANGLE
# ZINDENT := zindent min { TO distance P4 }
# LTO :: TO ++ ZINDENT atangle { DIRN + 180d }
# LTO :< TO@ANGLE
# LMID :: P2 ** 0.5 ++ P3 ** 0.5
# LMID :< DIRN - 180d
# FROM P1 P2 P3 P4 TO
}
PDF @Yield {}
}
}
import @Geometry
def @UWrapCurvePath
{
@BackEnd @Case {
PostScript @Yield {
{arrow @FromArrowLength arrowlength}
{arrow @ToArrowLength arrowlength}
"{" from "}" "{" to "}"
xindent zindent bias fbias tbias radius "ldiaguwrapcurvepath"
# DIRN := if cond { xcoord from??CTR < xcoord to??CTR }
# then { 180d } else { 0d }
# CLOCK := if cond { xcoord from??CTR < xcoord to??CTR }
# then { clockwise } else { anticlockwise }
# FROM :: from boundaryatangle DIRN
# ++ {arrow @FromArrowLength arrowlength} atangle DIRN
# FROM :< DIRN
# TO :: to boundaryatangle { DIRN + 180d }
# ++ {arrow @ToArrowLength arrowlength} atangle { DIRN + 180d }
# TO :< DIRN
#
# XP1 := FROM ++ {fbias max 0} atangle DIRN
# XP4 := TO ++ {tbias max 0} atangle { DIRN + 180d }
# YC := ycoord { from boundaryatangle 90d } max
# ycoord { to boundaryatangle 90d }
# + { bias max 0 }
# XP2 := { xcoord XP1 YC }
# XP3 := { xcoord XP4 YC }
#
# RP1 := radius min { XP1 distance FROM } min
# { { XP1 distance XP2 } / 2 }
# XP1PRE := XP1 ++ RP1 atangle { XP1 angleto FROM }
# XP1POST := XP1 ++ RP1 atangle { XP1 angleto XP2 }
# XP1CTR := XP1PRE ++ RP1 atangle { XP1 angleto XP2 }
# P1 :: XP1CTR ++ RP1 atangle { XP1CTR angleto XP1 }
# P1 :< XP1CTR angleto P1 + DIRN + 90d
#
# RP2 := radius min { { XP1 distance XP2 } / 2 }
# min { { XP2 distance XP3 } / 2 }
# XP2PRE := XP2 ++ RP2 atangle { XP2 angleto XP1 }
# XP2POST := XP2 ++ RP2 atangle { XP2 angleto XP3 }
# XP2CTR := XP2PRE ++ RP2 atangle { XP2 angleto XP3 }
# P2 :: XP2CTR ++ RP2 atangle { XP2CTR angleto XP2 }
# P2 :< XP2CTR angleto P2 + DIRN + 90d
#
# RP3 := radius min { { XP2 distance XP3 } / 2 }
# min { { XP3 distance XP4 } / 2 }
# XP3PRE := XP3 ++ RP3 atangle { XP3 angleto XP2 }
# XP3POST := XP3 ++ RP3 atangle { XP3 angleto XP4 }
# XP3CTR := XP3PRE ++ RP3 atangle { XP3 angleto XP4 }
# P3 :: XP3CTR ++ RP3 atangle { XP3CTR angleto XP3 }
# P3 :< XP3CTR angleto P3 + DIRN + 90d
#
# RP4 := radius min { { XP4 distance XP3 } / 2 }
# min { XP4 distance TO }
# XP4PRE := XP4 ++ RP4 atangle { XP4 angleto XP3 }
# XP4POST := XP4 ++ RP4 atangle { XP4 angleto TO }
# XP4CTR := XP4PRE ++ RP4 atangle { XP4 angleto TO }
# P4 :: XP4CTR ++ RP4 atangle { XP4CTR angleto XP4 }
# P4 :< XP4CTR angleto P4 + DIRN + 90d
#
# XINDENT := xindent min { FROM distance XP1PRE }
# LFROM :: FROM ++ XINDENT atangle DIRN
# LFROM :< FROM@ANGLE
#
# LMID :: XP2 ** 0.5 ++ XP3 ** 0.5
# LMID :< DIRN - 180d
#
# ZINDENT := zindent min { TO distance XP4POST }
# LTO :: TO ++ ZINDENT atangle { DIRN + 180d }
# LTO :< TO@ANGLE
#
# FROM LFROM
# XP1PRE [XP1CTR CLOCK] XP1POST
# XP2PRE [XP2CTR CLOCK] XP2POST
# LMID
# XP3PRE [XP3CTR CLOCK] XP3POST
# XP4PRE [XP4CTR CLOCK] XP4POST
# LTO TO
}
PDF @Yield {}
}
}
import @Geometry
def @Path
{
path @Case {
line @Yield @LinePath
doubleline @Yield @DoubleLinePath
{ acurve curve } @Yield @ACurvePath
ccurve @Yield @CCurvePath
bezier @Yield @BezierPath
vhline @Yield @VHLinePath
vhcurve @Yield @VHCurvePath
hvline @Yield @HVLinePath
hvcurve @Yield @HVCurvePath
lvrline @Yield @LVRLinePath
lvrcurve @Yield @LVRCurvePath
rvlline @Yield @RVLLinePath
rvlcurve @Yield @RVLCurvePath
dwrapline @Yield @DWrapLinePath
dwrapcurve @Yield @DWrapCurvePath
uwrapline @Yield @UWrapLinePath
uwrapcurve @Yield @UWrapCurvePath
else @Yield {
path
from { from }
to { to }
bias { bias }
fbias { fbias }
tbias { tbias }
radius { radius }
xindent { xindent }
zindent { zindent }
frompt { frompt }
topt { topt }
arrow { arrow }
arrowlength { arrowlength }
}
}
}
def @FromLabel
{
@DoLabel
which { "f" }
label { fromlabel @Else @FromArrow }
labelmargin { fromlabelmargin }
labelfont { fromlabelfont }
labelbreak { fromlabelbreak }
labelformat { fromlabelformat @Body }
labelpos { fromlabelpos }
labelprox { fromlabelprox }
labelangle { fromlabelangle }
labelctr { fromlabelctr }
labeladjust { fromlabeladjust }
}
def @ToLabel
{
@DoLabel
which { "t" }
label { tolabel @Else @ToArrow }
labelmargin { tolabelmargin }
labelfont { tolabelfont }
labelbreak { tolabelbreak }
labelformat { tolabelformat @Body }
labelpos { tolabelpos }
labelprox { tolabelprox }
labelangle { tolabelangle }
labelctr { tolabelctr }
labeladjust { tolabeladjust }
}
def @Direct
{
pathstyle @Case {
{ "/ldiagsolid" "/ldiagdashed" "/ldiagcdashed"
"/ldiagdotted" "/ldiagnoline" } @Yield 1
else @Yield 0
}
}
@BackEnd @Case {
PostScript @Yield {
@Null & # so that preceding space gets chewed up
{
@Direct "ldiaglinkbegin [" @Path "]" pathdashlength
"[" pathstyle "]" pathwidth "ldiaglinkend"
}
@Graphic
{
/ { fromlabel @Else @FromArrow} @IfNonEmpty @FromLabel
/ { xlabel @Else linklabel } @IfNonEmpty @XLabel
/ { ylabel @Else linklabel } @IfNonEmpty @YLabel
/ { zlabel @Else linklabel } @IfNonEmpty @ZLabel
/ { tolabel @Else @ToArrow } @IfNonEmpty @ToLabel
}
}
PDF @Yield {}
}
}
def @ObjectLink
precedence 90
associativity left
left x
named treehsep { treehsep }
named treevsep { treevsep }
named format
named x {}
named y {}
named insinuatelink {}
named treehsep {}
named treevsep {}
{ x | y | insinuatelink }
import @Geometry named path
named from {}
named to {}
named bias {}
named fbias {}
named tbias {}
named radius {}
named xindent {}
named zindent {}
named frompt {}
named topt {}
named arrow {}
named arrowlength {}
{ path
from { from }
to { to }
bias { bias }
fbias { fbias }
tbias { tbias }
radius { radius }
xindent { xindent }
zindent { zindent }
frompt { frompt }
topt { topt }
arrow { arrow }
arrowlength { arrowlength }
}
import @Geometry named basefrom { }
import @Geometry named baseto { }
import @Geometry named from { }
import @Geometry named to { }
import @Geometry named bias { bias }
import @Geometry named fbias { fbias }
import @Geometry named tbias { tbias }
import @Geometry named radius { radius }
import @Geometry named xindent { xindent }
import @Geometry named zindent { zindent }
import @Geometry named frompt { frompt }
import @Geometry named topt { topt }
named pathstyle
named solid { "/ldiagsolid" }
named dashed { "/ldiagdashed" }
named cdashed { "/ldiagcdashed" }
named dotted { "/ldiagdotted" }
named noline { "/ldiagnoline" }
{ pathstyle }
import @Geometry named pathdashlength { pathdashlength }
import @Geometry named pathwidth
named thin { 0.04 ft }
named medium { 0.08 ft }
named thick { 0.12 ft }
{ pathwidth }
import @Geometry named pathgap
named thin { 0.08 ft }
named medium { 0.16 ft }
named thick { 0.24 ft }
{ pathgap }
named arrow { arrow }
named arrowstyle { arrowstyle }
named arrowwidth { arrowwidth }
named arrowlength { arrowlength }
named linklabel { linklabel }
named linklabelmargin { linklabelmargin }
named linklabelfont { linklabelfont }
named linklabelbreak { linklabelbreak }
named linklabelformat right @Body { linklabelformat @Body }
import @Geometry named linklabelpos { linklabelpos }
named linklabelprox { linklabelprox }
import @Geometry named linklabelangle { linklabelangle }
named linklabelctr { linklabelctr }
import @Geometry named linklabeladjust { linklabeladjust }
named xlabel { xlabel }
named xlabelmargin { xlabelmargin }
named xlabelfont { xlabelfont }
named xlabelbreak { xlabelbreak }
named xlabelformat right @Body { xlabelformat @Body }
import @Geometry named xlabelpos { xlabelpos }
named xlabelprox { xlabelprox }
import @Geometry named xlabelangle { xlabelangle }
named xlabelctr { xlabelctr }
import @Geometry named xlabeladjust { xlabeladjust }
named ylabel { ylabel }
named ylabelmargin { ylabelmargin }
named ylabelfont { ylabelfont }
named ylabelbreak { ylabelbreak }
named ylabelformat right @Body { ylabelformat @Body }
import @Geometry named ylabelpos { ylabelpos }
named ylabelprox { ylabelprox }
import @Geometry named ylabelangle { ylabelangle }
named ylabelctr { ylabelctr }
import @Geometry named ylabeladjust { ylabeladjust }
named zlabel { zlabel }
named zlabelmargin { zlabelmargin }
named zlabelfont { zlabelfont }
named zlabelbreak { zlabelbreak }
named zlabelformat right @Body { zlabelformat @Body }
import @Geometry named zlabelpos { zlabelpos }
named zlabelprox { zlabelprox }
import @Geometry named zlabelangle { zlabelangle }
named zlabelctr { zlabelctr }
import @Geometry named zlabeladjust { zlabeladjust }
named fromlabel { fromlabel }
named fromlabelmargin { fromlabelmargin }
named fromlabelfont { fromlabelfont }
named fromlabelbreak { fromlabelbreak }
named fromlabelformat right @Body { fromlabelformat @Body }
import @Geometry named fromlabelpos { fromlabelpos }
named fromlabelprox { fromlabelprox }
import @Geometry named fromlabelangle { fromlabelangle }
named fromlabelctr { fromlabelctr }
import @Geometry named fromlabeladjust { fromlabeladjust }
named tolabel { tolabel }
named tolabelmargin { tolabelmargin }
named tolabelfont { tolabelfont }
named tolabelbreak { tolabelbreak }
named tolabelformat right @Body { tolabelformat @Body }
import @Geometry named tolabelpos { tolabelpos }
named tolabelprox { tolabelprox }
import @Geometry named tolabelangle { tolabelangle }
named tolabelctr { tolabelctr }
import @Geometry named tolabeladjust{ tolabeladjust }
right y
{
def @From
{
from @Case {
"" @Yield basefrom
else @Yield { basefrom"@"from }
}
}
def @To
{
to @Case {
"" @Yield baseto
else @Yield { baseto"@"to }
}
}
format
x { x }
y { y }
treehsep { treehsep }
treevsep { treevsep }
insinuatelink {
@Link
from { @From }
to { @To }
bias { bias }
fbias { fbias }
tbias { tbias }
radius { radius }
xindent { xindent }
zindent { zindent }
frompt { frompt }
topt { topt }
path { path
from { @From }
to { @To }
bias { bias }
fbias { fbias }
tbias { tbias }
radius { radius }
xindent { xindent }
zindent { zindent }
frompt { frompt }
topt { topt }
arrow { arrow }
arrowlength { arrowlength }
}
pathstyle { pathstyle }
pathdashlength { pathdashlength }
pathwidth { pathwidth }
pathgap { pathgap }
arrow { arrow }
arrowstyle { arrowstyle }
arrowwidth { arrowwidth }
arrowlength { arrowlength }
linklabel { linklabel }
linklabelmargin { linklabelmargin }
linklabelfont { linklabelfont }
linklabelbreak { linklabelbreak }
linklabelformat { linklabelformat @Body }
linklabelpos { linklabelpos }
linklabelprox { linklabelprox }
linklabelangle { linklabelangle }
linklabelctr { linklabelctr }
linklabeladjust { linklabeladjust }
xlabel { xlabel }
xlabelmargin { xlabelmargin }
xlabelfont { xlabelfont }
xlabelbreak { xlabelbreak }
xlabelformat { xlabelformat @Body }
xlabelpos { xlabelpos }
xlabelprox { xlabelprox }
xlabelangle { xlabelangle }
xlabelctr { xlabelctr }
xlabeladjust { xlabeladjust }
ylabel { ylabel }
ylabelmargin { ylabelmargin }
ylabelfont { ylabelfont }
ylabelbreak { ylabelbreak }
ylabelformat { ylabelformat @Body }
ylabelpos { ylabelpos }
ylabelprox { ylabelprox }
ylabelangle { ylabelangle }
ylabelctr { ylabelctr }
ylabeladjust { ylabeladjust }
zlabel { zlabel }
zlabelmargin { zlabelmargin }
zlabelfont { zlabelfont }
zlabelbreak { zlabelbreak }
zlabelformat { zlabelformat @Body }
zlabelpos { zlabelpos }
zlabelprox { zlabelprox }
zlabelangle { zlabelangle }
zlabelctr { zlabelctr }
zlabeladjust { zlabeladjust }
fromlabel { fromlabel }
fromlabelmargin { fromlabelmargin }
fromlabelfont { fromlabelfont }
fromlabelbreak { fromlabelbreak }
fromlabelformat { fromlabelformat @Body }
fromlabelpos { fromlabelpos }
fromlabelprox { fromlabelprox }
fromlabelangle { fromlabelangle }
fromlabelctr { fromlabelctr }
fromlabeladjust { fromlabeladjust }
tolabel { tolabel }
tolabelmargin { tolabelmargin }
tolabelfont { tolabelfont }
tolabelbreak { tolabelbreak }
tolabelformat { tolabelformat @Body }
tolabelpos { tolabelpos }
tolabelprox { tolabelprox }
tolabelangle { tolabelangle }
tolabelctr { tolabelctr }
tolabeladjust { tolabeladjust }
}
}
#######################################################################
# #
# Abbreviations for standard link types #
# #
#######################################################################
macro @Line { @Link path { line } }
macro @DoubleLine { @Link path { doubleline } }
macro @Arrow { @Link path { line } arrow { yes } }
macro @DoubleArrow { @Link path {doubleline} arrow { yes } }
macro @Curve { @Link path { curve } }
macro @CurveArrow { @Link path { curve } arrow { yes } }
macro @ACurve { @Link path { acurve } }
macro @ACurveArrow { @Link path { acurve } arrow { yes } }
macro @CCurve { @Link path { ccurve } }
macro @CCurveArrow { @Link path { ccurve } arrow { yes } }
macro @Bezier { @Link path { bezier } }
macro @BezierArrow { @Link path { bezier } arrow { yes } }
macro @HVLine { @Link path { hvline } }
macro @HVArrow { @Link path { hvline } arrow { yes } }
macro @VHLine { @Link path { vhline } }
macro @VHArrow { @Link path { vhline } arrow { yes } }
macro @HVCurve { @Link path { hvcurve } }
macro @HVCurveArrow { @Link path { hvcurve } arrow { yes } }
macro @VHCurve { @Link path { vhcurve } }
macro @VHCurveArrow { @Link path { vhcurve } arrow { yes } }
macro @LVRLine { @Link path { lvrline } }
macro @LVRArrow { @Link path { lvrline } arrow { yes } }
macro @RVLLine { @Link path { rvlline } }
macro @RVLArrow { @Link path { rvlline } arrow { yes } }
macro @LVRCurve { @Link path { lvrcurve } }
macro @LVRCurveArrow { @Link path { lvrcurve } arrow { yes } }
macro @RVLCurve { @Link path { rvlcurve } }
macro @RVLCurveArrow { @Link path { rvlcurve } arrow { yes } }
macro @DWrapLine { @Link path { dwrapline} }
macro @DWrapArrow { @Link path { dwrapline} arrow { yes } }
macro @UWrapLine { @Link path { uwrapline} }
macro @UWrapArrow { @Link path { uwrapline} arrow { yes } }
macro @DWrapCurve { @Link path {dwrapcurve} }
macro @DWrapCurveArrow { @Link path {dwrapcurve} arrow { yes } }
macro @UWrapCurve { @Link path {uwrapcurve} }
macro @UWrapCurveArrow { @Link path {uwrapcurve} arrow { yes } }
#######################################################################
# #
# Tree code. #
# #
#######################################################################
export
@Node @Box @CurveBox @ShadowBox @Square @Diamond
@Polygon @Isosceles @Ellipse @Circle
@LeftSub @ZeroWidthLeftSub @RightSub @ZeroWidthRightSub
@FirstSub @NextSub @StubSub
def @Tree
named treehindent
named left { 0.0rt }
named ctr { 0.5rt }
named right { 1.0rt }
{ treehindent }
body x
{
macro @TNode { @@Node nodetag { T } }
macro @Node { @TNode }
macro @Box { @TNode outline { box } }
macro @CurveBox { @TNode outline { curvebox } }
macro @ShadowBox { @TNode outline { shadowbox } }
macro @Square { @TNode outline { square } }
macro @Diamond { @TNode outline { diamond } }
macro @Polygon { @TNode outline { polygon } }
macro @Isosceles { @TNode outline { isosceles } }
macro @Ellipse { @TNode outline { ellipse } }
macro @Circle { @TNode outline { circle } }
def fixroot
precedence 90
left root
{
|treehindent root
}
macro @LeftSub
{
@ObjectLink
basefrom { T }
baseto { L@T }
format { { /treevsep {L::y} } |treehsep x | insinuatelink }
}
macro @ZeroWidthLeftSub
{
@ObjectLink
basefrom { T }
baseto { L@T }
format { { /treevsep @ZeroWidth { {L::y} ^|treehsep } } |
x | insinuatelink }
}
macro @FirstSub
{
fixroot //
@ObjectLink
basefrom { T }
baseto { S@T }
format { //treevsep {S::y} | insinuatelink | }
}
macro @NextSub
{
@ObjectLink
basefrom { T }
baseto { S@T }
format { x |treehsep { / {S::y} | insinuatelink | } }
}
macro @RightSub
{
@ObjectLink
basefrom { T }
baseto { R@T }
format { x |treehsep { /treevsep {R::y} } | insinuatelink }
}
macro @ZeroWidthRightSub
{
@ObjectLink
basefrom { T }
baseto { R@T }
format { x | { /treevsep @ZeroWidth { |treehsep {R::y} } }
| insinuatelink }
}
macro @StubSub
{
@ObjectLink
basefrom { T }
baseto { T }
format { @VContract { |0.5rt x | // |0.5rt
S:: @BoxLabels @CatchTags y | } | insinuatelink }
# path { from S@T@SW S@T@SE to }
path {
P1:: S@SW
P2:: S@SE
FROM:: from boundaryatangle { from??CTR angleto P1 }
TO:: to boundaryatangle { to??CTR angleto P2 }
FROM P1 P2 TO
}
}
@HContract @VContract x
}
export
@Node @Box @CurveBox @ShadowBox @Square @Diamond
@Polygon @Isosceles @Ellipse @Circle
@LeftSub @ZeroWidthLeftSub @RightSub @ZeroWidthRightSub
@FirstSub @NextSub @StubSub
def @HTree
named treevindent
named top { 0.0rt }
named ctr { 0.5rt }
named foot { 1.0rt }
{ treevindent }
body x
{
macro @TNode { @@Node nodetag { T } }
macro @Node { @TNode }
macro @Box { @TNode outline { box } }
macro @CurveBox { @TNode outline { curvebox } }
macro @ShadowBox { @TNode outline { shadowbox } }
macro @Square { @TNode outline { square } }
macro @Diamond { @TNode outline { diamond } }
macro @Polygon { @TNode outline { polygon } }
macro @Isosceles { @TNode outline { isosceles } }
macro @Ellipse { @TNode outline { ellipse } }
macro @Circle { @TNode outline { circle } }
def fixroot
precedence 90
left root
{
/treevindent root
}
macro @LeftSub
{
@ObjectLink
basefrom { T }
baseto { L@T }
format { { |treehsep {L::y} } /treevsep x / insinuatelink }
}
macro @ZeroWidthLeftSub
{
@ObjectLink
basefrom { T }
baseto { L@T }
format { { |treehsep @ZeroWidth { {L::y} ^/treevsep } } /
x / insinuatelink }
}
macro @FirstSub
{
fixroot ||
@ObjectLink
basefrom { T }
baseto { S@T }
format { ||treehsep { {S::y} / insinuatelink / } }
}
macro @NextSub
{
@ObjectLink
basefrom { T }
baseto { S@T }
format { x /treevsep { | {S::y} { / insinuatelink / } } }
}
macro @RightSub
{
@ObjectLink
basefrom { T }
baseto { R@T }
format { x /treevsep { |treehsep {R::y} } / insinuatelink }
}
macro @ZeroWidthRightSub
{
@ObjectLink
basefrom { T }
baseto { R@T }
format { x / { |treehsep @ZeroWidth { /treevsep {R::y} } }
/ insinuatelink }
}
macro @StubSub
{
@ObjectLink
basefrom { T }
baseto { T }
format { @VContract { { /0.5rt x / } || { /0.5rt
S:: @BoxLabels @CatchTags y / } } / insinuatelink }
# path { from S@T@SW S@T@SE to }
path {
P1:: S@NE
P2:: S@SE
FROM:: from boundaryatangle { from??CTR angleto P1 }
TO:: to boundaryatangle { to??CTR angleto P2 }
FROM P1 P2 TO
}
}
@HContract @VContract x
}
#######################################################################
# #
# Syntax diagrams code #
# #
# Helper definitions; also skips #
# #
#######################################################################
def pslength right x { "("x") ldiagdecodelength" }
def pssyntaxgap { "("syntaxgap") ldiagdecodelength" }
def pssyntaxbias { "("syntaxbias") ldiagdecodelength" }
def pssyntaxradius { "("syntaxradius") ldiagdecodelength" }
def @ArrowLeftFrom left direction right pt
{
@Line arrow { direction } from { pt } to { pt -- { pssyntaxgap 0 } }
}
def @ArrowRightFrom left direction right pt
{
@Line arrow { direction } from { pt } to { pt ++ { pssyntaxgap 0 } }
}
def @ArrowUpFrom left direction right pt
{
@Line arrow { direction } from { pt } to { pt ++ { 0 pssyntaxgap } }
}
def @ArrowDownFrom left direction right pt
{
@Line arrow { direction } from { pt } to { pt -- { 0 pssyntaxgap } }
}
macro @LineLeftFrom { no @ArrowLeftFrom }
macro @LineRightFrom { no @ArrowRightFrom }
macro @LineUpFrom { no @ArrowUpFrom }
macro @LineDownFrom { no @ArrowDownFrom }
macro @Right { "1p" }
macro @Up { "2p" }
macro @Left { "3p" }
macro @Down { "4p" }
macro @CurrDirection { @CurrZUnit }
def @GoRight right x { @Right @ZUnit x }
def @GoUp right x { @Up @ZUnit x }
def @GoLeft right x { @Left @ZUnit x }
def @GoDown right x { @Down @ZUnit x }
def @GoReverse right x
{
@CurrDirection @Case {
@Right @Yield @GoLeft x
@Up @Yield @GoDown x
@Left @Yield @GoRight x
@Down @Yield @GoUp x
}
}
def @LabelMarks right x {
@HContract @VContract @ANode
outline {
NMK:: { xmark ysize }
SMK:: { xmark 0 }
WMK:: { 0 ymark }
EMK:: { xsize ymark }
NW:: { 0 ysize }
SW:: { 0 0 }
SE:: { xsize 0 }
NE:: { xsize ysize }
}
font {}
margin { 0c }
vstrut { no }
outlinestyle { noline }
halign { mark }
valign { mark }
x
}
def @HSkip
{
OX:: @LabelMarks { syntaxgap @Wide {} }
/ @Line from { "OX@WMK" } to { "OX@EMK" }
}
def @VSkip
{
OX:: @LabelMarks { syntaxgap @High {} }
/ @Line from { "OX@NMK" } to { "OX@SMK" }
}
def @Skip
{
@CurrDirection @Case {
{ @Left @Right } @Yield @HSkip
{ @Up @Down } @Yield @VSkip
}
}
def @LRLine right x
{
@HContract @VContract { @HSkip | x | @HSkip }
}
def @UDLine right x
{
@HContract @VContract { @VSkip / x / @VSkip }
}
#######################################################################
# #
# Ordinary starts: @StartRight, @StartUp, @StartLeft, @StartDown #
# #
#######################################################################
def @StartRight right x
{
@VContract {
@LabelMarks {
|syntaxgap @GoRight x |syntaxgap
}
/ @LineRightFrom WMK
/ back @ArrowLeftFrom EMK
}
}
def @StartUp right x
{
@VContract {
@LabelMarks {
^/syntaxgap @GoUp x /syntaxgap
}
/ @LineUpFrom SMK
/ back @ArrowDownFrom NMK
}
}
def @StartLeft right x
{
@VContract {
@LabelMarks {
|syntaxgap @GoLeft x |syntaxgap
}
/ @LineLeftFrom EMK
/ back @ArrowRightFrom WMK
}
}
def @StartDown right x
{
@VContract {
@LabelMarks {
^/syntaxgap @GoDown x /syntaxgap
}
/ @LineDownFrom NMK
/ back @ArrowUpFrom SMK
}
}
#######################################################################
# #
# Fancy starts: @StartRightRight, @StartRightDown #
# #
#######################################################################
def @StartRightRight
named A {}
named B {}
{
AA:: @LabelMarks { @HSkip & @GoRight A }
//syntaxgap
//syntaxgap
|syntaxgap |syntaxgap |syntaxgap |syntaxgap |syntaxgap |syntaxgap
CC:: @LabelMarks {}
//syntaxgap
//syntaxgap
|syntaxgap |syntaxgap |syntaxgap |syntaxgap |syntaxgap |syntaxgap
BB:: @LabelMarks { @GoRight B & @HSkip }
// @RVLCurve from { AA@EMK } to { CC@WMK }
bias { pssyntaxbias } radius { pssyntaxradius }
// @LVRCurve from { CC@WMK } to { BB@WMK }
bias { pssyntaxbias } radius { pssyntaxradius }
back @ArrowLeftFrom BB@EMK
}
def @StartRightDown
named A {}
named B {}
{
@HContract @VContract {
/ BB:: @LabelMarks |syntaxgap AA::@LabelMarks @GoRight A |syntaxbias
/syntaxgap | |
/syntaxgap | |
}
/ @Line from { BB@EMK } to { AA@WMK }
/ @RVLCurve from { AA@EMK } to { xcoord AA@EMK pssyntaxgap }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @HVCurve from { xcoord AA@EMK pssyntaxgap } to { 0 0 }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @GoDown B
/ @VSkip
/ CC:: @LabelMarks {}
/ back @ArrowUpFrom CC@NMK
}
#######################################################################
# #
# Cells: @XCell, @ACell, @BCell, @CCell #
# #
#######################################################################
def @RightCell right x
{
@VContract {
@LabelMarks {
|syntaxgap x |syntaxgap
}
/ forward @ArrowRightFrom WMK
/ @LineLeftFrom EMK
}
}
def @LeftCell right x
{
@VContract {
@LabelMarks {
|syntaxgap x |syntaxgap
}
/ forward @ArrowLeftFrom EMK
/ @LineRightFrom WMK
}
}
def @DownCell right x
{
@VContract {
@LabelMarks {
^/syntaxgap x /syntaxgap
}
/ forward @ArrowDownFrom NMK
/ @LineUpFrom SMK
}
}
def @UpCell right x
{
@VContract {
@LabelMarks {
^/syntaxgap x /syntaxgap
}
/ forward @ArrowUpFrom SMK
/ @LineDownFrom NMK
}
}
def @XCell right x
{
@CurrDirection @Case {
@Right @Yield @RightCell x
@Up @Yield @UpCell x
@Left @Yield @LeftCell x
@Down @Yield @DownCell x
}
}
macro @ACell { @XCell @ANode }
macro @BCell { @XCell @BNode }
macro @CCell { @XCell @CNode }
#######################################################################
# #
# @Sequence #
# #
#######################################################################
def @Sequence
named A {}
named B {}
named C {}
named D {}
named E {}
named F {}
named G {}
named H {}
named I {}
named J {}
named K {}
named L {}
{
@CurrDirection @Case {
@Right @Yield
@HContract { A | B | C | D | E | F | G | H | I | J | K | L }
@Up @Yield
@VContract { L / K / J / I / H / G / F / E / D / C / B / A }
@Left @Yield
@HContract { L | K | J | I | H | G | F | E | D | C | B | A }
@Down @Yield
@VContract { A / B / C / D / E / F / G / H / I / J / K / L }
}
}
#######################################################################
# #
# @Select and @Optional #
# #
#######################################################################
def @Select
named A {}
named B {}
named C {}
named D {}
named E {}
named F {}
named G {}
named H {}
named I {}
named J {}
named K {}
named L {}
{
def @RLFirstOrMiddle
left label
named i { 0i }
named al { no }
named ar { no }
right x
{
{|i @HContract { |syntaxgap label:: @LabelMarks x |syntaxgap }}
// @Line from { label"@WMK" } to { 0 ycoord label"@WMK" }
arrow { al }
// @Line from { label"@EMK" } to { xsize ycoord label"@EMK" }
arrow { ar }
}
def @UDFirstOrMiddle
left label
named i { 0i }
named au { no }
named ad { no }
right x
{
{/i @VContract { /syntaxgap label:: @LabelMarks x /syntaxgap }}
|| @Line from { label"@NMK" } to { xcoord label"@NMK" ysize }
arrow { au }
|| @Line from { label"@SMK" } to { xcoord label"@SMK" 0 }
arrow { ad }
}
def @RLLast
left label
named i { 0i }
named al { no }
named ar { no }
right x
{
{|i @HContract { |syntaxgap label:: @LabelMarks x |syntaxgap }}
// @HVCurve from { label"@WMK" } to { 0 ycoord "AX@WMK" }
arrow { al } bias { pssyntaxbias } radius { pssyntaxradius }
// @HVCurve from { label"@EMK" } to { xsize ycoord "AX@WMK" }
arrow { ar } bias { pssyntaxbias } radius { pssyntaxradius }
}
def @UDLast
left label
named i { 0i }
named au { no }
named ad { no }
right x
{
{/i @VContract { /syntaxgap label:: @LabelMarks x /syntaxgap }}
|| @VHCurve from { label"@NMK" } to { xcoord "AX@NMK" ysize }
arrow { au } bias { pssyntaxbias } radius { pssyntaxradius }
|| @VHCurve from { label"@SMK" } to { xcoord "AX@SMK" 0 }
arrow { ad } bias { pssyntaxbias } radius { pssyntaxradius }
}
def @DirectedSelect
named @First left label right x {}
named @Middle left label right x {}
named @Last left label right x {}
named @Join precedence 90 left x right y {}
{
def @LastIsA
{
A
}
def @LastIsB
{
AX @First A
@Join BX @Last B
}
def @LastIsC
{
AX @First A
@Join BX @Middle B
@Join CX @Last C
}
def @LastIsD
{
AX @First A
@Join BX @Middle B
@Join CX @Middle C
@Join DX @Last D
}
def @LastIsE
{
AX @First A
@Join BX @Middle B
@Join CX @Middle C
@Join DX @Middle D
@Join EX @Last E
}
def @LastIsF
{
AX @First A
@Join BX @Middle B
@Join CX @Middle C
@Join DX @Middle D
@Join EX @Middle E
@Join FX @Last F
}
def @UpToF
{
AX @First A
@Join BX @Middle B
@Join CX @Middle C
@Join DX @Middle D
@Join EX @Middle E
@Join FX @Middle F
}
def @LastIsG
{
@UpToF
@Join GX @Last G
}
def @LastIsH
{
@UpToF
@Join GX @Middle G
@Join HX @Last H
}
def @LastIsI
{
@UpToF
@Join GX @Middle G
@Join HX @Middle H
@Join IX @Last I
}
def @LastIsJ
{
@UpToF
@Join GX @Middle G
@Join HX @Middle H
@Join IX @Middle I
@Join JX @Last J
}
def @LastIsK
{
@UpToF
@Join GX @Middle G
@Join HX @Middle H
@Join IX @Middle I
@Join JX @Middle J
@Join KX @Last K
}
def @LastIsL
{
@UpToF
@Join GX @Middle G
@Join HX @Middle H
@Join IX @Middle I
@Join JX @Middle J
@Join KX @Middle K
@Join LX @Last L
}
def @TryA { A @Case { {} @Yield @Skip else @Yield @LastIsA } }
def @TryB { B @Case { {} @Yield @TryA else @Yield @LastIsB } }
def @TryC { C @Case { {} @Yield @TryB else @Yield @LastIsC } }
def @TryD { D @Case { {} @Yield @TryC else @Yield @LastIsD } }
def @TryE { E @Case { {} @Yield @TryD else @Yield @LastIsE } }
def @TryF { F @Case { {} @Yield @TryE else @Yield @LastIsF } }
def @TryG { G @Case { {} @Yield @TryF else @Yield @LastIsG } }
def @TryH { H @Case { {} @Yield @TryG else @Yield @LastIsH } }
def @TryI { I @Case { {} @Yield @TryH else @Yield @LastIsI } }
def @TryJ { J @Case { {} @Yield @TryI else @Yield @LastIsJ } }
def @TryK { K @Case { {} @Yield @TryJ else @Yield @LastIsK } }
def @TryL { L @Case { {} @Yield @TryK else @Yield @LastIsL } }
@TryL
}
def @RightSelect
{
@LRLine @DirectedSelect
@First { label @RLFirstOrMiddle x }
@Middle { label @RLFirstOrMiddle ar { yes } x }
@Last { label @RLLast ar { yes } x }
@Join { x //syntaxgap y }
}
def @UpSelect
{
@UDLine @DirectedSelect
@First { label @UDFirstOrMiddle i { 1r } x }
@Middle { label @UDFirstOrMiddle i { 1r } au { yes } x }
@Last { label @UDLast i { 1r } au { yes } x }
@Join { x ||syntaxgap y }
}
def @LeftSelect
{
@LRLine @DirectedSelect
@First { label @RLFirstOrMiddle i { 1r } x }
@Middle { label @RLFirstOrMiddle i { 1r } al { yes } x }
@Last { label @RLLast i { 1r } al { yes } x }
@Join { x //syntaxgap y }
}
def @DownSelect
{
@UDLine @DirectedSelect
@First { label @UDFirstOrMiddle x }
@Middle { label @UDFirstOrMiddle ad { yes } x }
@Last { label @UDLast ad { yes } x }
@Join { x ||syntaxgap y }
}
@CurrDirection @Case {
@Right @Yield @RightSelect
@Up @Yield @UpSelect
@Left @Yield @LeftSelect
@Down @Yield @DownSelect
}
}
def @Optional right x
{
@Select A { @Skip } B { x }
}
#######################################################################
# #
# @OptionalDiverted #
# #
#######################################################################
def @DownRightOptionalDiverted right x
{
@UDLine {
OX:: @LabelMarks {
|syntaxgap AX:: @LabelMarks @GoRight x |syntaxbias
/syntaxgap
}
/ @Line from { "OX@NW" } to { "OX@SW" }
/ @Line from { "OX@WMK" } to { "OX@IN@AX@WMK" }
/ @RVLCurveArrow from { "OX@IN@AX@EMK" } to { "OX@SW" }
bias { pssyntaxbias } radius { pssyntaxradius }
}
}
def @UpRightOptionalDiverted right x
{
@UDLine {
OX:: @LabelMarks {
^/syntaxgap
|syntaxgap AX:: @LabelMarks @GoRight x |syntaxbias
}
/ @Line from { "OX@NW" } to { "OX@SW" }
/ @Line from { "OX@WMK" } to { "OX@IN@AX@WMK" }
/ @RVLCurveArrow from { "OX@IN@AX@EMK" } to { "OX@NW" }
bias { pssyntaxbias } radius { pssyntaxradius }
}
}
def @RightDownOptionalDiverted right x
{
@LRLine {
OX:: @LabelMarks {
{ /syntaxgap AX:: @LabelMarks @GoDown x /syntaxbias }
|syntaxgap
}
/ @Line from { "OX@NW" } to { "OX@NE" }
/ @Line from { "OX@NMK" } to { "OX@IN@AX@NMK" }
/ @VHCurve from {"OX@IN@AX@SMK"} to { "OX@SE"--{pssyntaxgap 0} }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @HVCurve from { "OX@SE" -- {pssyntaxgap 0} } to { "OX@NE" }
arrow { yes } bias { pssyntaxbias } radius { pssyntaxradius }
}
}
def @LeftDownOptionalDiverted right x
{
@LRLine {
OX:: @LabelMarks {
^|syntaxgap
{ /syntaxgap AX:: @LabelMarks @GoDown x /syntaxbias }
}
/ @Line from { "OX@NW" } to { "OX@NE" }
/ @Line from { "OX@NMK" } to { "OX@IN@AX@NMK" }
/ @VHCurve from {"OX@IN@AX@SMK"} to { "OX@SW"++{pssyntaxgap 0} }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @HVCurve from { "OX@SW" ++ {pssyntaxgap 0} } to { "OX@NW" }
arrow { yes } bias { pssyntaxbias } radius { pssyntaxradius }
}
}
def @OptionalDiverted right x
{
@CurrDirection @Case {
@Right @Yield @RightDownOptionalDiverted x
@Up @Yield @UpRightOptionalDiverted x
@Left @Yield @LeftDownOptionalDiverted x
@Down @Yield @DownRightOptionalDiverted x
}
}
#######################################################################
# #
# @Diverted #
# #
#######################################################################
def @DownRightDiverted right x
{
@UDLine {
OX:: @LabelMarks {
|syntaxgap AX:: @LabelMarks @GoRight x |syntaxbias
^/syntaxgap
/syntaxgap
}
/ @VHCurve from { "OX@NW" } to { "OX@IN@AX@WMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @RVLCurve from { "OX@IN@AX@EMK" }
to { xcoord "OX@IN@AX@WMK" ycoord "OX@EMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @HVCurve from { xcoord "OX@IN@AX@WMK" ycoord "OX@EMK" }
to { "OX@SW" } bias { pssyntaxbias } radius {pssyntaxradius}
}
}
def @UpRightDiverted right x
{
@UDLine {
OX:: @LabelMarks {
^/syntaxgap
/syntaxgap
|syntaxgap AX:: @LabelMarks @GoRight x |syntaxbias
}
/ @VHCurve from { "OX@SW" } to { "OX@IN@AX@WMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @RVLCurve from { "OX@IN@AX@EMK" }
to { xcoord "OX@IN@AX@WMK" ycoord "OX@EMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @HVCurve from { xcoord "OX@IN@AX@WMK" ycoord "OX@EMK" }
to { "OX@NW" } bias { pssyntaxbias } radius {pssyntaxradius}
}
}
def @RightDownDiverted right x
{
@LRLine {
OX:: @LabelMarks {
{ /syntaxgap AX:: @LabelMarks @GoDown x /syntaxbias }
^|syntaxgap
|syntaxgap
}
/ @HVCurve from { "OX@NW" } to { "OX@IN@AX@NMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @VHCurve from { "OX@IN@AX@SMK" }
to { xcoord "OX@IN@AX@EMK" ycoord "OX@SMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @HVCurve from { xcoord "OX@IN@AX@EMK" ycoord "OX@SMK" }
to { "OX@IN@AX@EMK" ++ { pssyntaxgap 0 } }
bias { pssyntaxbias } radius {pssyntaxradius}
/ @VHCurve from { "OX@IN@AX@EMK" ++ { pssyntaxgap 0 } }
to { "OX@NE" } bias { pssyntaxbias } radius {pssyntaxradius}
}
}
def @LeftDownDiverted right x
{
@LRLine {
OX:: @LabelMarks {
|syntaxgap
^|syntaxgap
{ /syntaxgap AX:: @LabelMarks @GoDown x /syntaxbias }
}
/ @HVCurve from { "OX@NE" } to { "OX@IN@AX@NMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @VHCurve from { "OX@IN@AX@SMK" }
to { xcoord "OX@IN@AX@WMK" ycoord "OX@SMK" }
bias { pssyntaxbias } radius { pssyntaxradius }
/ @HVCurve from { xcoord "OX@IN@AX@WMK" ycoord "OX@SMK" }
to { "OX@IN@AX@WMK" -- { pssyntaxgap 0 } }
bias { pssyntaxbias } radius {pssyntaxradius}
/ @VHCurve from { "OX@IN@AX@WMK" -- { pssyntaxgap 0 } }
to { "OX@NW" } bias { pssyntaxbias } radius {pssyntaxradius}
}
}
def @Diverted right x
{
@CurrDirection @Case {
@Right @Yield @RightDownDiverted x
@Up @Yield @UpRightDiverted x
@Left @Yield @LeftDownDiverted x
@Down @Yield @DownRightDiverted x
}
}
#######################################################################
# #
# @RepeatDiverted #
# #
#######################################################################
def @RepeatDiverted right x
{
# this implementation exploits the coincidental similarity
# of @RepeatDiverted to @OptionalDiverted
@CurrDirection @Case {
@Right @Yield @LeftDownOptionalDiverted x
@Up @Yield @DownRightOptionalDiverted x
@Left @Yield @RightDownOptionalDiverted x
@Down @Yield @UpRightOptionalDiverted x
}
}
#######################################################################
# #
# @Loop and @Repeat #
# #
#######################################################################
def @Loop
named A {}
named B {}
{
def @LeftOrRightLoop
named al { no }
named ar { no }
{
@LRLine {
@HContract @VContract { OX:: @LabelMarks {
{ |syntaxgap AX:: @LabelMarks A |syntaxgap }
//syntaxgap
{ |0.5rt BX:: @LabelMarks @GoReverse B |syntaxgap }
} }
/ @Line from { "OX@WMK" } to { "OX@IN@AX@WMK" }
/ @Line from { "OX@EMK" } to { "OX@IN@AX@EMK" }
/ @HVCurve from { "OX@IN@BX@EMK" } to { "OX@EMK" }
arrow { ar } bias {pssyntaxbias} radius {pssyntaxradius}
/ @HVCurve from { "OX@IN@BX@WMK" } to { "OX@WMK" }
arrow { al } bias {pssyntaxbias} radius {pssyntaxradius}
}
}
def @UpOrDownLoop
named au { no }
named ad { no }
{
@UDLine {
@HContract @VContract { OX:: @LabelMarks {
{ /syntaxgap AX:: @LabelMarks A /syntaxgap }
||syntaxgap
{ /0.5rt BX:: @LabelMarks @GoReverse B /syntaxgap }
} }
/ @Line from { "OX@NMK" } to { "OX@IN@AX@NMK" }
/ @Line from { "OX@SMK" } to { "OX@IN@AX@SMK" }
/ @VHCurve from { "OX@IN@BX@NMK" } to { "OX@NMK" }
arrow { au } bias {pssyntaxbias} radius {pssyntaxradius}
/ @VHCurve from { "OX@IN@BX@SMK" } to { "OX@SMK" }
arrow { ad } bias {pssyntaxbias} radius {pssyntaxradius}
}
}
@CurrDirection @Case {
@Right @Yield @LeftOrRightLoop al { yes }
@Up @Yield @UpOrDownLoop ad { yes }
@Left @Yield @LeftOrRightLoop ar { yes }
@Down @Yield @UpOrDownLoop au { yes }
}
}
def @Repeat right x
{
@Loop
A { x }
B { @Skip }
}
#######################################################################
# #
# @LoopOpposite and @RepeatOpposite #
# #
#######################################################################
def @LoopOpposite
named A {}
named B {}
{
def @LeftOrRightLoopOpposite
named al { no }
named ar { no }
{
@LRLine {
@HContract @VContract { OX:: @LabelMarks {
{ |0.5rt BX:: @LabelMarks @GoReverse B |syntaxgap }
^//syntaxgap
{ |syntaxgap AX:: @LabelMarks A |syntaxgap }
} }
/ @Line from { "OX@WMK" } to { "OX@IN@AX@WMK" }
/ @Line from { "OX@EMK" } to { "OX@IN@AX@EMK" }
/ @HVCurve from { "OX@IN@BX@EMK" } to { "OX@EMK" }
arrow { ar } bias {pssyntaxbias} radius {pssyntaxradius}
/ @HVCurve from { "OX@IN@BX@WMK" } to { "OX@WMK" }
arrow { al } bias {pssyntaxbias} radius {pssyntaxradius}
}
}
def @UpOrDownLoopOpposite
named au { no }
named ad { no }
{
@UDLine {
@HContract @VContract { OX:: @LabelMarks {
{ /0.5rt BX:: @LabelMarks @GoReverse B /syntaxgap }
^||syntaxgap
{ /syntaxgap AX:: @LabelMarks A /syntaxgap }
} }
/ @Line from { "OX@NMK" } to { "OX@IN@AX@NMK" }
/ @Line from { "OX@SMK" } to { "OX@IN@AX@SMK" }
/ @VHCurve from { "OX@IN@BX@NMK" } to { "OX@NMK" }
arrow { au } bias {pssyntaxbias} radius {pssyntaxradius}
/ @VHCurve from { "OX@IN@BX@SMK" } to { "OX@SMK" }
arrow { ad } bias {pssyntaxbias} radius {pssyntaxradius}
}
}
@CurrDirection @Case {
@Right @Yield @LeftOrRightLoopOpposite al { yes }
@Up @Yield @UpOrDownLoopOpposite ad { yes }
@Left @Yield @LeftOrRightLoopOpposite ar { yes }
@Down @Yield @UpOrDownLoopOpposite au { yes }
}
}
def @RepeatOpposite right x
{
@LoopOpposite
A { x }
B { @Skip }
}
#######################################################################
# #
# Value of whole diagram #
# #
#######################################################################
def @DiagValue right x
{
@BackEnd @Case {
PostScript @Yield {
{
save @Case {
{ yes Yes } @Yield "grestore save gsave"
else @Yield {}
}
maxlabels "ldiagbegin"
//
"ldiagend"
save @Case {
{ yes Yes } @Yield "restore"
else @Yield {}
}
} @Graphic x }
PDF @Yield {}
}
}
title @Case {
"--titledft--" @Yield @DiagValue @Body
else @Yield { title titleformat @DiagValue @Body }
}
@End @Diag
macro @SyntaxDiag {
@Diag
avalign { mark }
avstrut { yes }
amargin { 0.2f }
aoutline { box }
afont { Italic }
bvalign { mark }
bvstrut { yes }
bmargin { 0.2f }
boutline { curvebox }
bfont { Bold }
cvalign { mark }
cvstrut { yes }
cmargin { 0.2f }
coutline { circle }
chsize { 1f }
arrowlength { 0.4f }
}
}