(FILECREATED "30-Apr-87 10:24:03" {PHYLUM}<LISPUSERS>KOTO>EQUATIONFORMS.;1 85410 changes to: (FNS EQ.SumGroup EQ.IntegralGroup AB.RealPosition AB.PointPos AB.SidePosition AB.PlaceRegion AB.AdjustToLL AB.OppositeSide AB.RegionToBox AB.BoxToRegion AB.RelativePos AB.BiggerRegion AB.Check AB.PositionRegion AB.Position2Regions EQ.Group EQ.GroupCreate EQ.Make.group EQ.enclosure EQ.EnclosureEdit EQ.EnclosureKind EQ.EnclosureSide EQ.angles EQ.bars EQ.braces EQ.brackets EQ.parentheses EQ.enclosureForm EQ.DrawBraces EQ.DrawParentheses EQ.Matrix EQ.layout EQ.MatrixAdd EQ.MatrixCreate EQ.MatrixDelete EQ.MatrixEdit EQ.MatrixGetMenu EQ.Fraction EQ.Script EQ.MaxMin EQ.Root) (VARS EQUATIONFORMSCOMS) previous date: "18-Mar-86 15:43:29" {PHYLUM}<LISP>KOTO>LISPUSERS>EQUATIONFORMS.;1) (* Copyright (c) 1986, 1987 by Xerox Corporation. All rights reserved.) (PRETTYCOMPRINT EQUATIONFORMSCOMS) (RPAQQ EQUATIONFORMSCOMS ((* * ATTACHEDBOX module: Part 1 of 5) (* Utility functions to manipulate attached regions) (* These functions use two sets of coords: global coords in which positions are given w.r.t. the lower left corner of a box, and side coords in which positions are given w.r.t. a particular side of the box. For the side coords, the origin is at the point on the side closest to the l.l. corner of the box, the x-axis points along the side toward the other end, and the y-axis points away from the box region) (FNS AB.RealPosition AB.PointPos AB.SidePosition AB.PlaceRegion AB.AdjustToLL AB.OppositeSide AB.RegionToBox AB.BoxToRegion AB.RelativePos AB.BiggerRegion AB.Check AB.PositionRegion AB.Position2Regions) (* * EQGROUP module: Part 2 of 5) (* group equation functions) (FNS EQ.Group EQ.GroupCreate EQ.Make.group) (* set up data definitions) (P (EQIO.AddType (QUOTE group) (QUOTE EQ.Group) 1 (QUOTE (objectProps (enclosureKind NIL enclosureSide NIL) pieceNames ("item") wholeEditFn EQ.EnclosureEdit initialPropFn EQ.GroupCreate)))) (* * specific enclosure data) (RECORDS EQ.EnclosureData) (FNS EQ.AddEnclosure EQ.GetEnclosureData) (* set up data for enclosures) (P (EQ.AddEnclosure (QUOTE angles) (FUNCTION EQ.angles) "< angle brackets >") (EQ.AddEnclosure (QUOTE bars) (FUNCTION EQ.bars) "| bars |") (EQ.AddEnclosure (QUOTE braces) (FUNCTION EQ.braces) "{ braces }") (EQ.AddEnclosure (QUOTE brackets) (FUNCTION EQ.brackets) "[ brackets ]") (EQ.AddEnclosure (QUOTE parentheses) (FUNCTION EQ.parentheses) "( parentheses )") (EQIO.TypeProp (QUOTE group) (QUOTE defaultEnclosure) (QUOTE brackets))) (* * general enclosure functions) (FNS EQ.enclosure EQ.EnclosureCreate EQ.EnclosureEdit EQ.EnclosureKind EQ.EnclosureSide) (* * enclosure form functions) (FNS EQ.angles EQ.bars EQ.braces EQ.brackets EQ.parentheses EQ.enclosureForm EQ.enclosureWidth) (* * enclosure drawing functions) (FNS EQ.DrawAngles EQ.DrawBars EQ.DrawBraces EQ.DrawBrackets EQ.DrawParentheses) (* * EQMATRIX module: Part 3 of 5) (* matrix equation functions) (FNS EQ.Matrix EQ.Make.matrix EQ.layout EQ.MatrixAdd EQ.MatrixChanged EQ.MatrixCreate EQ.MatrixDelete EQ.MatrixEdit EQ.MatrixGetMenu EQ.MatrixSelect) (INITVARS (EQ.Matrix.MaxPieces 100)) (GLOBALVARS EQ.Matrix.MaxPieces) (P (EQIO.AddType (QUOTE matrix) (QUOTE EQ.Matrix) 1 (QUOTE (objectProps (rows 1 columns 1 enclosureKind NIL enclosureSide NIL) variable? T wholeEditFn EQ.MatrixEdit specialSelectFn EQ.MatrixSelect initialPropFn EQ.MatrixCreate changeFn EQ.MatrixChanged)))) (* * EQNFORMS module: Part 4 of 5) (* fraction) (FNS EQ.Fraction EQ.Make.fraction) (* * sum group) (FNS EQ.SumGroup EQ.Make.sum EQ.Make.product EQ.Make.union EQ.Make.intersection) (* * integral group) (FNS EQ.IntegralGroup EQ.Make.integral EQ.Make.lineIntegral) (* * super- and sub- scripts) (FNS EQ.Script EQ.Make.sub/superscripts) (* * max/min/limit etc) (FNS EQ.MaxMin EQ.Make.max/min) (* * utilities) (FNS EQ.StreamSize EQ.UseNS?) (GLOBALVARS EQ.UseNSChars) (* EQ.UseNSChars = NIL to use press fonts for display) (INITVARS EQ.UseNSChars) (P (EQIO.AddType (QUOTE fraction) (QUOTE EQ.Fraction) 2 (QUOTE (pieceNames ("numerator" "denominator")))) (EQIO.AddType (QUOTE sum) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "summand")))) (EQIO.AddType (QUOTE product) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "factor")))) (EQIO.AddType (QUOTE union) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "set")))) (EQIO.AddType (QUOTE intersection) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "set")))) (EQIO.AddType (QUOTE integral) (QUOTE EQ.IntegralGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("lower limit" "upper limit" "integrand")))) (EQIO.AddType (QUOTE lineIntegral) (QUOTE EQ.IntegralGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("lower limit" "upper limit" "integrand") menuLabel "line integral"))) (EQIO.AddType (QUOTE sub/superscripts) (QUOTE EQ.Script) 5 (QUOTE (initialData (0 -1 -1 -1 -1) pieceNames ("main value" "right subscript" "right superscript" "left subscript" "left superscript")))) (EQIO.AddType (QUOTE max/min) (QUOTE EQ.MaxMin) 3 (QUOTE (initialData (0 -2 0) pieceNames ("function" "index" "value") menuLabel "max min limit")))) (* * EQROOT module: Part 5 of 5) (FNS EQ.Root EQ.Make.root) (FNS EQ.DrawRadicalSign) (P (EQIO.AddType (QUOTE root) (QUOTE EQ.Root) 2 (QUOTE (pieceNames ("radicand" "index") initialData (0 -1))))))) (* * ATTACHEDBOX module: Part 1 of 5) (* Utility functions to manipulate attached regions) (* These functions use two sets of coords: global coords in which positions are given w.r.t. the lower left corner of a box, and side coords in which positions are given w.r.t. a particular side of the box. For the side coords, the origin is at the point on the side closest to the l.l. corner of the box, the x-axis points along the side toward the other end, and the y-axis points away from the box region) (DEFINEQ (AB.RealPosition (LAMBDA (pos box side) (* THH " 8-May-85 11:31") (* returns position of pt. relative to l.l. corner of box given position relative to specified side of box) (SELECTQ side ((top bottom) (create POSITION XCOORD ←(fetch XCOORD of pos) YCOORD ←(COND ((EQ side (QUOTE top)) (PLUS (fetch YSIZE of box) (fetch YCOORD of pos))) (T (MINUS (fetch YCOORD of pos)))))) ((left right) (create POSITION YCOORD ←(fetch XCOORD of pos) XCOORD ←(COND ((EQ side (QUOTE right)) (PLUS (fetch XSIZE of box) (fetch YCOORD of pos))) (T (MINUS (fetch YCOORD of pos)))))) NIL))) (AB.PointPos (LAMBDA (box side pt) (* THH " 8-May-85 11:34") (* returns position of pt relative to side -- pt is an atom specifying relative position along the side) (PROG ((horizSide (OR (EQ side (QUOTE top)) (EQ side (QUOTE bottom))))) (RETURN (create POSITION XCOORD ←(SELECTQ pt (low (* lower end of side) 0) (display (* display pt of side) (COND (horizSide 0) (T (fetch YDESC of box)))) (center (* center of side) (IQUOTIENT (COND (horizSide (fetch XSIZE of box)) (T (fetch YSIZE of box))) 2)) (high (* upper end of side) (COND (horizSide (fetch XSIZE of box)) (T (fetch YSIZE of box)))) NIL) YCOORD ← 0))))) (AB.SidePosition (LAMBDA (pos box side) (* THH " 8-May-85 11:32") (* returns position of pt rel. to side given position rel. to l.l. corner of box) (SELECTQ side ((top bottom) (create POSITION XCOORD ←(fetch XCOORD of pos) YCOORD ←(COND ((EQ side (QUOTE top)) (DIFFERENCE (fetch YCOORD of pos) (fetch YSIZE of box))) (T (MINUS (fetch YCOORD of pos)))))) ((left right) (create POSITION XCOORD ←(fetch YCOORD of pos) YCOORD ←(COND ((EQ side (QUOTE right)) (DIFFERENCE (fetch XCOORD of pos) (fetch XSIZE of box))) (T (MINUS (fetch XCOORD of pos)))))) NIL))) (AB.PlaceRegion (LAMBDA (mainBox side mainPt addBox addPt gap shift) (* THH "10-May-85 16:51") (* returns placed region relative to l.l. corner of main box when addBox is placed as specified) (PROG ((posMainPt (AB.PointPos mainBox side mainPt)) (opposite (AB.OppositeSide side)) posAddPt posSide) (SETQ posAddPt (create POSITION XCOORD ←(PLUS (fetch XCOORD of posMainPt) shift) YCOORD ←(PLUS (fetch YCOORD of posMainPt) gap))) (SETQ posSide (AB.PointPos addBox opposite addPt)) (replace XCOORD of posSide with (DIFFERENCE (fetch XCOORD of posAddPt) (fetch XCOORD of posSide))) (replace YCOORD of posSide with (fetch YCOORD of posAddPt)) (SETQ posSide (AB.AdjustToLL (AB.RealPosition posSide mainBox side) addBox side)) (RETURN (create REGION LEFT ←(fetch XCOORD of posSide) BOTTOM ←(fetch YCOORD of posSide) WIDTH ←(fetch XSIZE of addBox) HEIGHT ←(fetch YSIZE of addBox)))))) (AB.AdjustToLL (LAMBDA (pos addBox side) (* THH "10-May-85 14:58") (* gets position of l.l. corner of addBox w.r.t. l.l of main box given pos of side opposite side of main box) (SELECTQ side ((top right) NIL) (left (replace XCOORD of pos with (DIFFERENCE (fetch XCOORD of pos) (fetch XSIZE of addBox)))) (bottom (replace YCOORD of pos with (DIFFERENCE (fetch YCOORD of pos) (fetch YSIZE of addBox)))) NIL) pos)) (AB.OppositeSide (LAMBDA (side) (* THH " 8-May-85 14:11") (SELECTQ side (top (QUOTE bottom)) (bottom (QUOTE top)) (left (QUOTE right)) (right (QUOTE left)) NIL))) (AB.RegionToBox (LAMBDA (region displayYPos) (* thh: "13-May-85 10:16") (* returns image box corresponding to region whose y display position, relative to (0,0) is given by displayYPos) (COND ((NOT displayYPos) (SETQ displayYPos 0))) (create IMAGEBOX XSIZE ←(fetch WIDTH of region) YSIZE ←(fetch HEIGHT of region) YDESC ←(DIFFERENCE displayYPos (fetch BOTTOM of region)) XKERN ← 0))) (AB.BoxToRegion (LAMBDA (box cornerXPos cornerYPos) (* thh: "13-May-85 09:54") (* returns region corresponding to image box whose l.l. corner is positioned at cornerXPos, cornerYPos -- if cornerYPos is NIL then cornerXPos should be a position) (COND ((NOT cornerYPos) (SETQ cornerYPos (fetch YCOORD of cornerXPos)) (SETQ cornerXPos (fetch XCOORD of cornerXPos)))) (create REGION LEFT ← cornerXPos BOTTOM ← cornerYPos WIDTH ←(fetch XSIZE of box) HEIGHT ←(fetch YSIZE of box)))) (AB.RelativePos (LAMBDA (region bigRegion yShift) (* thh: "13-May-85 10:27") (* returns relative position of l.l. of region w.r.t. l.l. of bigRegion) (create POSITION XCOORD ←(DIFFERENCE (fetch LEFT of region) (fetch LEFT of bigRegion)) YCOORD ←(PLUS (DIFFERENCE (fetch BOTTOM of region) (fetch BOTTOM of bigRegion)) yShift)))) (AB.BiggerRegion (LAMBDA (region extra) (* THH "23-May-85 14:03") (* creates a region that has extra space all around) (* extra should be nonnegative) (COND ((OR (NOT extra) (ZEROP extra)) region) (T (create REGION LEFT ←(DIFFERENCE (fetch LEFT of region) extra) BOTTOM ←(DIFFERENCE (fetch BOTTOM of region) extra) WIDTH ←(PLUS (fetch WIDTH of region) (TIMES 2 extra)) HEIGHT ←(PLUS (fetch HEIGHT of region) (TIMES 2 extra))))))) (AB.Check (LAMBDA (region regionList side clear) (* THH "23-May-85 14:02") (* moves region away from side if it overlaps any regions in regionList) (COND ((NOT clear) (SETQ clear 0))) (COND ((GREATERP clear 0) (SETQ regionList (for r in regionList collect (AB.BiggerRegion r clear))))) (* must go through list repeatedly since moving region could cause it to overlap previous regions) (repeatwhile overlap bind overlap do (SETQ overlap NIL) (for r in regionList do (COND ((REGIONSINTERSECTP region r) (SETQ overlap T) (SELECTQ side (top (replace BOTTOM of region with (PLUS (fetch BOTTOM of r) (fetch HEIGHT of r)))) (bottom (replace BOTTOM of region with (DIFFERENCE (fetch BOTTOM of r) (fetch HEIGHT of region)))) (left (replace LEFT of region with (DIFFERENCE (fetch LEFT of r) (fetch WIDTH of region) ))) (right (replace LEFT of region with (PLUS (fetch LEFT of r) (fetch WIDTH of r)))) (SHOULDNT)))))) region)) (AB.PositionRegion (LAMBDA (mainBox addedRegions side mainPt addBox addPt gap shift clear) (* thh: " 9-Jan-86 10:00") (* positions addBox next to side of mainBox so that addPt on the added box is at the specified relative position to the mainPt on the main box, then moves addBox away from mainBox if necessary to avoid being within distance clear of added regions on other sides as specified in addedRegions. Returns (region newAddedRegions) where region is region of added box w.r.t. l.l. corner of mainBox and newAddedRegions includes this new box to prevent future additions from overlapping it) (PROG ((place (AB.Check (AB.PlaceRegion mainBox side mainPt addBox addPt gap shift) addedRegions side clear))) (RETURN (CONS place addedRegions))))) (AB.Position2Regions (LAMBDA (mainBox addedRegions side highBox highPt lowBox lowPt highGap lowGap highShift lowShift clear) (* thh: " 9-Jan-86 10:00") (* positions highBox and lowBox next to side on mainBox -- moves the boxes apart if they are closer than clear apart, and moves them away from mainBox if they overlap previous regions as specfied by addedRegions) (* returns (highRegion lowRegion newAddedRegions) where regions are w.r.t. l.l. corner of mainBox and newAddedRegions includes the added regions) (PROG (placeHigh placeLow) (SETQ placeHigh (AB.PlaceRegion mainBox side (QUOTE high) highBox highPt highGap highShift)) (SETQ placeLow (AB.PlaceRegion mainBox side (QUOTE low) lowBox lowPt lowGap lowShift)) (COND ((NOT clear) (SETQ clear 0))) (COND ((REGIONSINTERSECTP placeHigh (AB.BiggerRegion placeLow clear)) (* move regions apart) (PROG (shift totalSize) (* if the two added regions overlap then separate them) (SELECTQ side ((top bottom) (SETQ shift (DIFFERENCE (PLUS (fetch LEFT of placeLow) (fetch WIDTH of placeLow) clear) (fetch LEFT of placeHigh))) (COND ((GREATERP shift 0) (SETQ totalSize (PLUS (fetch WIDTH of placeLow) (fetch WIDTH of placeHigh))) (add (fetch LEFT of placeLow) (MINUS (FIX (PLUS .5 (FQUOTIENT (TIMES shift (fetch WIDTH of placeLow)) totalSize))))) (add (fetch LEFT of placeHigh) (FIX (PLUS .5 (FQUOTIENT (TIMES shift (fetch WIDTH of placeHigh)) totalSize))))))) ((left right) (SETQ shift (DIFFERENCE (PLUS (fetch BOTTOM of placeLow) (fetch HEIGHT of placeLow) clear) (fetch BOTTOM of placeHigh))) (COND ((GREATERP shift 0) (SETQ totalSize (PLUS (fetch HEIGHT of placeLow) (fetch HEIGHT of placeHigh))) (add (fetch BOTTOM of placeLow) (MINUS (FIX (PLUS .5 (FQUOTIENT (TIMES shift (fetch HEIGHT of placeLow)) totalSize))))) (add (fetch BOTTOM of placeHigh) (FIX (PLUS .5 (FQUOTIENT (TIMES shift (fetch HEIGHT of placeHigh)) totalSize))))))) (SHOULDNT))))) (SETQ placeLow (AB.Check placeLow addedRegions side clear)) (SETQ placeHigh (AB.Check placeHigh addedRegions side clear)) (RETURN (CONS placeHigh (CONS placeLow addedRegions)))))) ) (* * EQGROUP module: Part 2 of 5) (* group equation functions) (DEFINEQ (EQ.Group (LAMBDA (eqnObj imageStream draw?) (* THH "12-Jul-85 08:24") (* form function for group -- one argument with enclosure) (LET ((innerBox (FS.Box (EQIO.EqnData eqnObj 1) imageStream)) enclose pos) (SETQ enclose (EQ.enclosure innerBox eqnObj imageStream draw?)) (SETQ pos (CDR enclose)) (add (fetch YCOORD of pos) (fetch YDESC of innerBox)) (EQIO.MakeSpec (CAR enclose) (LIST (EQIO.MakeDataSpec pos)))))) (EQ.GroupCreate (LAMBDA NIL (* thh: " 1-Jul-85 14:57") (EQ.EnclosureCreate T))) (EQ.Make.group (LAMBDA (data enclosureKind enclosureSide fontSpec) (* thh: " 9-Jan-86 10:24") (EQN.Make (QUOTE group) (LIST data) fontSpec (LIST (QUOTE enclosureKind) enclosureKind (QUOTE enclosureSide) enclosureSide)))) ) (* set up data definitions) (EQIO.AddType (QUOTE group) (QUOTE EQ.Group) 1 (QUOTE (objectProps (enclosureKind NIL enclosureSide NIL) pieceNames ("item") wholeEditFn EQ.EnclosureEdit initialPropFn EQ.GroupCreate))) (* * specific enclosure data) [DECLARE: EVAL@COMPILE (RECORD EQ.EnclosureData (formFn label)) ] (DEFINEQ (EQ.AddEnclosure (LAMBDA (kind formFn label) (* THH "12-Jul-85 08:18") (* adds data for new form of enclosure) (LET ((enclosures (EQIO.TypeProp (QUOTE group) (QUOTE enclosures))) (newValue (create EQ.EnclosureData formFn ← formFn label ← label))) (COND (enclosures (LISTPUT enclosures kind newValue)) (T (SETQ enclosures (LIST kind newValue)))) (EQIO.TypeProp (QUOTE group) (QUOTE enclosures) enclosures) (EQIO.TypeProp (QUOTE group) (QUOTE kindMenu) NIL)))) (EQ.GetEnclosureData (LAMBDA (kind) (* THH "12-Jul-85 08:19") (LISTGET (EQIO.TypeProp (QUOTE group) (QUOTE enclosures)) kind))) ) (* set up data for enclosures) (EQ.AddEnclosure (QUOTE angles) (FUNCTION EQ.angles) "< angle brackets >") (EQ.AddEnclosure (QUOTE bars) (FUNCTION EQ.bars) "| bars |") (EQ.AddEnclosure (QUOTE braces) (FUNCTION EQ.braces) "{ braces }") (EQ.AddEnclosure (QUOTE brackets) (FUNCTION EQ.brackets) "[ brackets ]") (EQ.AddEnclosure (QUOTE parentheses) (FUNCTION EQ.parentheses) "( parentheses )") (EQIO.TypeProp (QUOTE group) (QUOTE defaultEnclosure) (QUOTE brackets)) (* * general enclosure functions) (DEFINEQ (EQ.enclosure (LAMBDA (innerBox eqnObj imageStream draw?) (* THH "12-Jul-85 08:32") (* returns (outerBox . pos) where outerBox is box with enclosures and pos is position of l.l. corner of inner box wrt l.l. corner of outer box) (* if draw? is non-NIL, draws the enclosures) (LET ((kind (OR (EQIO.EqnProperty eqnObj (QUOTE enclosureKind)) (EQIO.TypeProp (QUOTE group) (QUOTE defaultEnclosure)))) (which (EQIO.EqnProperty eqnObj (QUOTE enclosureSide)))) (COND ((NOT (OR (EQ which (QUOTE left)) (EQ which (QUOTE right)))) (SETQ which NIL))) (LET ((formFn (fetch (EQ.EnclosureData formFn) of (EQ.GetEnclosureData kind)))) (COND (formFn (* note: use of kind arg allows same formFn to be used for different enclosures) (APPLY* formFn innerBox imageStream draw? which kind)) (T (* no enclosure so outer box is same as inner box) (CONS innerBox (create POSITION XCOORD ← 0 YCOORD ← 0)))))))) (EQ.EnclosureCreate (LAMBDA (getWhich?) (* thh: " 1-Jul-85 14:46") (* returns prop list describing desired enclosure) (* if getWhich? is non-NIL also asks for side specification for enclosure) (LET ((kind (EQ.EnclosureKind)) which) (COND (getWhich? (SETQ which (EQ.EnclosureSide)) (LIST (QUOTE enclosureKind) kind (QUOTE enclosureSide) which)) (T (LIST (QUOTE enclosureKind) kind)))))) (EQ.EnclosureEdit (LAMBDA (eqnObj) (* thh: " 1-Jul-85 14:55") (* allows type of enclosure to be changed) (* returns non-NIL if object changed) (LET ((editMenu (EQIO.TypeProp (QUOTE group) (QUOTE editMenu))) newValue) (COND ((NOT (type? MENU editMenu)) (SETQ editMenu (create MENU CENTERFLG ← T TITLE ← "change what?" ITEMS ←(QUOTE (("symbol" (QUOTE kind)) ("which side" (QUOTE side)))))) (EQIO.TypeProp (QUOTE group) (QUOTE editMenu) editMenu))) (SELECTQ (MENU editMenu) (kind (COND ((SETQ newValue (EQ.EnclosureKind)) (EQIO.EqnProperty eqnObj (QUOTE enclosureKind) newValue) T) (T NIL))) (side (COND ((SETQ newValue (EQ.EnclosureSide)) (EQIO.EqnProperty eqnObj (QUOTE enclosureSide) newValue) T) (T NIL))) NIL)))) (EQ.EnclosureKind (LAMBDA NIL (* THH "12-Jul-85 08:39") (* gets desired kind of enclosure) (LET ((kindMenu (EQIO.TypeProp (QUOTE group) (QUOTE kindMenu)))) (COND ((NOT (type? MENU kindMenu)) (SETQ kindMenu (create MENU CENTERFLG ← T ITEMS ←(LET ((enclosures (EQIO.TypeProp (QUOTE group) (QUOTE enclosures) ))) (while enclosures bind kind data collect (SETQ kind (CAR enclosures)) (SETQ data (CADR enclosures)) (SETQ enclosures (CDDR enclosures)) (LIST (fetch (EQ.EnclosureData label) of data) (KWOTE kind)))) TITLE ← "enclosures")) (EQIO.TypeProp (QUOTE group) (QUOTE kindMenu) kindMenu))) (MENU kindMenu)))) (EQ.EnclosureSide (LAMBDA NIL (* thh: " 1-Jul-85 14:48") (* gets desired side for enclosure) (LET ((whichMenu (EQIO.TypeProp (QUOTE group) (QUOTE whichMenu)))) (COND ((NOT (type? MENU whichMenu)) (SETQ whichMenu (create MENU ITEMS ←(QUOTE (left right both)) TITLE ← "Which side?")) (EQIO.TypeProp (QUOTE group) (QUOTE whichMenu) whichMenu))) (MENU whichMenu)))) ) (* * enclosure form functions) (DEFINEQ (EQ.angles (LAMBDA (innerBox imageStream draw? which) (* thh: "19-Aug-85 10:05") (LET ((size (EQ.StreamSize imageStream)) Hgap Hex Vgap Vex width height descent spacing overlap) (SETQ Hex size) (SETQ Vgap size) (SETQ Vex Hex) (SETQ height (PLUS (fetch YSIZE of innerBox) (TIMES 2 Vgap))) (SETQ width (EQ.enclosureWidth size height)) (SETQ Hgap (MAX (TIMES 3 size) (IQUOTIENT height 5))) (SETQ spacing (PLUS (fetch XSIZE of innerBox) (TIMES 2 (PLUS Hgap width)))) (SETQ descent (PLUS (fetch YDESC of innerBox) Vgap)) (SETQ overlap (MAX (TIMES 2 size) (IQUOTIENT (PLUS Hgap width) 2))) (* * draw angle brackets if requested) (COND (draw? (EQ.DrawAngles height descent spacing Hex width overlap imageStream which))) (* * determine outer box and position of inner box) (EQ.enclosureForm spacing Hex height Vex descent width NIL)))) (EQ.bars (LAMBDA (innerBox imageStream draw? which) (* THH "16-Jul-85 09:16") (LET ((size (EQ.StreamSize imageStream)) Hgap Hex Vgap Vex width height descent spacing) (SETQ Hgap (TIMES 2 size)) (SETQ Hex size) (SETQ Vgap Hgap) (SETQ Vex Hex) (SETQ height (PLUS (fetch YSIZE of innerBox) (TIMES 2 Vgap))) (SETQ width (EQ.enclosureWidth size height)) (SETQ spacing (PLUS (fetch XSIZE of innerBox) (TIMES 2 (PLUS Hgap width)))) (SETQ descent (PLUS (fetch YDESC of innerBox) Vgap)) (* * draw bars if requested) (COND (draw? (EQ.DrawBars height descent spacing Hex width imageStream which))) (* * determine outer box and position of inner box) (EQ.enclosureForm spacing Hex height Vex descent width NIL)))) (EQ.braces (LAMBDA (innerBox imageStream draw? which) (* THH "16-Jul-85 09:46") (LET ((size (EQ.StreamSize imageStream)) Hgap Hex Vgap Vex width height descent spacing overlap point space extra) (SETQ Vgap (TIMES 3 size)) (SETQ Hex size) (SETQ Vex Hex) (SETQ height (PLUS (fetch YSIZE of innerBox) (TIMES 2 Vgap))) (SETQ width (EQ.enclosureWidth size height)) (add height (TIMES 2 width)) (SETQ descent (PLUS (fetch YDESC of innerBox) Vgap width)) (SETQ Hgap (MAX (TIMES 4 size) (IQUOTIENT height 5))) (SETQ spacing (PLUS (fetch XSIZE of innerBox) (TIMES 2 (PLUS Hgap width)))) (SETQ overlap (PLUS Hgap width)) (SETQ point (PLUS size (IQUOTIENT overlap 2))) (SETQ space (IQUOTIENT overlap 2)) (SETQ extra space) (* * draw braces if requested) (COND (draw? (EQ.DrawBraces height descent spacing Hex width overlap extra point space imageStream which))) (* * determine outer box and position of inner box) (EQ.enclosureForm spacing Hex height Vex descent width T)))) (EQ.brackets (LAMBDA (innerBox imageStream draw? which) (* thh: "19-Aug-85 09:52") (LET ((size (EQ.StreamSize imageStream)) Hgap Hex Vgap Vex width height descent spacing overlap) (SETQ Hgap (TIMES 3 size)) (SETQ Hex size) (SETQ Vgap Hgap) (SETQ Vex Hex) (SETQ height (PLUS (fetch YSIZE of innerBox) (TIMES 2 Vgap))) (SETQ width (EQ.enclosureWidth size height)) (add height (TIMES 2 width)) (SETQ spacing (PLUS (fetch XSIZE of innerBox) (TIMES 2 (PLUS Hgap width)))) (SETQ descent (PLUS (fetch YDESC of innerBox) Vgap width)) (SETQ overlap (MAX (TIMES 3 size) (PLUS Hgap width))) (* * draw bars if requested) (COND (draw? (EQ.DrawBrackets height descent spacing Hex width overlap imageStream which))) (* * determine outer box and position of inner box) (EQ.enclosureForm spacing Hex height Vex descent width T)))) (EQ.parentheses (LAMBDA (innerBox imageStream draw? which) (* thh: "19-Aug-85 10:06") (LET ((size (EQ.StreamSize imageStream)) Hgap Hex Vgap Vex width height descent spacing overlap) (SETQ Vgap (TIMES 2 size)) (SETQ Hex size) (SETQ Vex Hex) (SETQ height (PLUS (fetch YSIZE of innerBox) (TIMES 2 Vgap))) (SETQ width (EQ.enclosureWidth size height)) (add height (TIMES 2 width)) (SETQ descent (PLUS (fetch YDESC of innerBox) Vgap width)) (SETQ Hgap (MAX (TIMES 2 size) (IQUOTIENT height 8))) (SETQ spacing (PLUS (fetch XSIZE of innerBox) (TIMES 2 (PLUS Hgap width)))) (SETQ overlap (MAX (TIMES 3 size) (IQUOTIENT (PLUS Hgap width) 2))) (* * draw braces if requested) (COND (draw? (EQ.DrawParentheses height descent spacing Hex width overlap imageStream which))) (* * determine outer box and position of inner box) (EQ.enclosureForm spacing Hex height Vex descent width T)))) (EQ.enclosureForm (LAMBDA (spacing Hex height Vex descent width verticalWidth?) (* THH "12-Jul-85 08:49") (* computes outer box and position of inner box from parameters -- verticalWidth? non-NIL means enclosure wraps under the box) (CONS (create IMAGEBOX XSIZE ←(PLUS spacing (TIMES 2 Hex)) YSIZE ←(PLUS height (TIMES 2 Vex)) YDESC ←(PLUS descent Vex) XKERN ← 0) (create POSITION XCOORD ←(PLUS Hgap width Hex) YCOORD ←(PLUS Vgap (COND (verticalWidth? width) (T 0)) Vex))))) (EQ.enclosureWidth (LAMBDA (size height) (* THH "16-Jul-85 09:15") (MAX size (IQUOTIENT height 100)))) ) (* * enclosure drawing functions) (DEFINEQ (EQ.DrawAngles (LAMBDA (height descent spacing xShift width overlap imageStream which) (* thh: "19-Aug-85 09:49") (* draws specified angle brackets on imageStream) (LET ((halfWidth (IQUOTIENT width 2)) (halfWidth1 (IQUOTIENT (SUB1 width) 2)) (lowerX (PLUS (DSPXPOSITION NIL imageStream) xShift)) (lowerY (DIFFERENCE (DSPYPOSITION NIL imageStream) descent)) top middle left right) (SETQ top (PLUS lowerY (SUB1 height))) (SETQ middle (PLUS lowerY (IQUOTIENT (SUB1 height) 2))) (* * left angle bracket) (COND ((NOT (EQ which (QUOTE right))) (SETQ left (PLUS lowerX overlap halfWidth)) (DRAWLINE left lowerY (PLUS lowerX halfWidth) middle width NIL imageStream) (DRAWLINE (PLUS lowerX halfWidth) middle left top width NIL imageStream))) (* * right angle bracket) (COND ((NOT (EQ which (QUOTE left))) (SETQ right (PLUS lowerX (SUB1 spacing) (MINUS (PLUS overlap halfWidth1)))) (DRAWLINE right lowerY (PLUS lowerX (SUB1 spacing) (MINUS halfWidth1)) middle width NIL imageStream) (DRAWLINE (PLUS lowerX (SUB1 spacing) (MINUS halfWidth1)) middle right top width NIL imageStream)))))) (EQ.DrawBars (LAMBDA (height descent spacing xShift width imageStream which) (* thh: "19-Aug-85 09:53") (* draws specified vertical bar on imageStream) (PROG ((halfWidth (IQUOTIENT width 2)) (halfWidth1 (IQUOTIENT (SUB1 width) 2)) (lowerX (PLUS (DSPXPOSITION NIL imageStream) xShift)) (lowerY (DIFFERENCE (DSPYPOSITION NIL imageStream) descent))) (* * left bar) (COND ((NOT (EQ which (QUOTE right))) (MOVETO (PLUS lowerX halfWidth1) lowerY imageStream) (RELDRAWTO 0 (SUB1 height) width NIL imageStream))) (* * right bar) (COND ((NOT (EQ which (QUOTE left))) (MOVETO (DIFFERENCE (PLUS lowerX spacing) halfWidth) lowerY imageStream) (RELDRAWTO 0 (SUB1 height) width NIL imageStream)))))) (EQ.DrawBraces (LAMBDA (height descent spacing xShift width overlap extra point space imageStream which) (* THH "16-Jul-85 09:20") (* draws specified brace on imageStream) (LET ((halfWidth (IQUOTIENT width 2)) (halfWidth1 (IQUOTIENT (SUB1 width) 2)) (lowerX (PLUS (DSPXPOSITION NIL imageStream) xShift)) (lowerY (DIFFERENCE (DSPYPOSITION NIL imageStream) descent)) top middle left1 left2 right1 right2) (SETQ top (PLUS lowerY (SUB1 height))) (SETQ middle (PLUS lowerY (IQUOTIENT (SUB1 height) 2))) (* * left brace) (COND ((NOT (EQ which (QUOTE right))) (SETQ left1 (PLUS lowerX (SUB1 overlap))) (SETQ left2 (PLUS lowerX (SUB1 point))) (DRAWCURVE (LIST (create POSITION XCOORD ← left1 YCOORD ← lowerY) (create POSITION XCOORD ← left2 YCOORD ←(PLUS lowerY extra)) (create POSITION XCOORD ← left2 YCOORD ←(DIFFERENCE middle (SUB1 space))) (create POSITION XCOORD ← lowerX YCOORD ← middle)) NIL width NIL imageStream) (DRAWCURVE (LIST (create POSITION XCOORD ← lowerX YCOORD ← middle) (create POSITION XCOORD ← left2 YCOORD ←(PLUS middle (SUB1 space))) (create POSITION XCOORD ← left2 YCOORD ←(DIFFERENCE top extra)) (create POSITION XCOORD ← left1 YCOORD ← top)) NIL width NIL imageStream))) (* * right brace) (COND ((NOT (EQ which (QUOTE left))) (SETQ right1 (PLUS lowerX (SUB1 spacing) (MINUS (SUB1 overlap)))) (SETQ right2 (PLUS lowerX (SUB1 spacing) (MINUS (SUB1 point)))) (DRAWCURVE (LIST (create POSITION XCOORD ← right1 YCOORD ← lowerY) (create POSITION XCOORD ← right2 YCOORD ←(PLUS lowerY extra)) (create POSITION XCOORD ← right2 YCOORD ←(DIFFERENCE middle (SUB1 space))) (create POSITION XCOORD ←(PLUS lowerX (SUB1 spacing)) YCOORD ← middle)) NIL width NIL imageStream) (DRAWCURVE (LIST (create POSITION XCOORD ←(PLUS lowerX (SUB1 spacing)) YCOORD ← middle) (create POSITION XCOORD ← right2 YCOORD ←(PLUS middle (SUB1 space))) (create POSITION XCOORD ← right2 YCOORD ←(DIFFERENCE top extra)) (create POSITION XCOORD ← right1 YCOORD ← top)) NIL width NIL imageStream)))))) (EQ.DrawBrackets (LAMBDA (height descent spacing xShift width overlap imageStream which) (* THH "12-Jul-85 09:06") (* draws specified bracket on imageStream) (PROG ((halfWidth (IQUOTIENT width 2)) (halfWidth1 (IQUOTIENT (SUB1 width) 2)) (lowerX (PLUS (DSPXPOSITION NIL imageStream) xShift)) (lowerY (DIFFERENCE (DSPYPOSITION NIL imageStream) descent))) (* * left bracket) (COND ((NOT (EQ which (QUOTE right))) (MOVETO (PLUS lowerX halfWidth1) lowerY imageStream) (RELDRAWTO 0 (SUB1 height) width NIL imageStream) (RELMOVETO 0 (MINUS halfWidth) imageStream) (RELDRAWTO overlap 0 width NIL imageStream) (MOVETO (PLUS lowerX (SUB1 width)) (PLUS lowerY halfWidth1) imageStream) (RELDRAWTO overlap 0 width NIL imageStream))) (* * right bracket) (COND ((NOT (EQ which (QUOTE left))) (MOVETO (DIFFERENCE (PLUS lowerX spacing) (PLUS overlap width)) (PLUS lowerY halfWidth1) imageStream) (RELDRAWTO overlap 0 width NIL imageStream) (RELMOVETO halfWidth1 (MINUS halfWidth1) imageStream) (RELDRAWTO 0 (SUB1 height) width NIL imageStream) (RELMOVETO 0 (MINUS halfWidth) imageStream) (RELDRAWTO (MINUS overlap) 0 width NIL imageStream)))))) (EQ.DrawParentheses (LAMBDA (height descent spacing xShift width overlap imageStream which) (* THH "12-Jul-85 09:06") (* draws specified parenthesis on imageStream) (LET ((halfWidth (IQUOTIENT width 2)) (halfWidth1 (IQUOTIENT (SUB1 width) 2)) (lowerX (PLUS (DSPXPOSITION NIL imageStream) xShift)) (lowerY (DIFFERENCE (DSPYPOSITION NIL imageStream) descent)) top middle left right) (SETQ top (PLUS lowerY (SUB1 height))) (SETQ middle (PLUS lowerY (IQUOTIENT (SUB1 height) 2))) (* * left parenthesis) (COND ((NOT (EQ which (QUOTE right))) (SETQ left (PLUS lowerX overlap halfWidth)) (DRAWCURVE (LIST (create POSITION XCOORD ← left YCOORD ← lowerY) (create POSITION XCOORD ←(PLUS lowerX halfWidth) YCOORD ← middle) (create POSITION XCOORD ← left YCOORD ← top)) NIL width NIL imageStream))) (* * right parenthesis) (COND ((NOT (EQ which (QUOTE left))) (SETQ right (PLUS lowerX (SUB1 spacing) (MINUS (PLUS overlap halfWidth1)))) (DRAWCURVE (LIST (create POSITION XCOORD ← right YCOORD ← lowerY) (create POSITION XCOORD ←(PLUS lowerX (SUB1 spacing) (MINUS halfWidth1)) YCOORD ← middle) (create POSITION XCOORD ← right YCOORD ← top)) NIL width NIL imageStream)))))) ) (* * EQMATRIX module: Part 3 of 5) (* matrix equation functions) (DEFINEQ (EQ.Matrix (LAMBDA (eqnObj imageStream draw?) (* THH "12-Jul-85 09:50") (* form function for matrix) (* this equation form allows a variable number of parts arranged and stored in rows) (LET ((layout (EQ.layout eqnObj imageStream)) enclose specs) (SETQ enclose (EQ.enclosure (EQIO.GetBox layout) eqnObj imageStream draw?)) (* * enclose of form (outerBox . pos) -- must now shift positions of individual pieces in layout (assumes no selection region in layout -- it would also need to be shifted)) (SETQ specs (EQIO.GetDataSpecList layout)) (for dataSpec in specs bind pos (xShift ←(fetch (POSITION XCOORD) of (CDR enclose))) (yShift ←(fetch (POSITION YCOORD) of (CDR enclose)) ) do (SETQ pos (EQIO.GetDataPosition dataSpec)) (add (fetch (POSITION XCOORD) of pos) xShift) (add (fetch (POSITION YCOORD) of pos) yShift)) (EQIO.MakeSpec (CAR enclose) specs)))) (EQ.Make.matrix (LAMBDA (rows columns dataList enclosureKind enclosureSide fontSpec) (* thh: " 9-Jan-86 10:23") (* * may want to call initial prop fn???) (LET ((numPieces (TIMES rows columns))) (EQN.Make (QUOTE matrix) dataList fontSpec (LIST (QUOTE numPieces) numPieces (QUOTE rows) rows (QUOTE columns) columns (QUOTE enclosureKind) enclosureKind (QUOTE enclosureSide) enclosureSide))))) (EQ.layout (LAMBDA (eqnObj imageStream) (* THH "12-Jul-85 10:26") (* form function for table of parts) (* this equation form allows a variable number of parts arranged and stored in rows) (* layout defined by rowGap -- distance between rows, colGap -- distance between columns, shift -- distance of center above baseline) (LET ((size (EQ.StreamSize imageStream)) (columns (EQIO.EqnProperty eqnObj (QUOTE columns))) (rows (EQIO.EqnProperty eqnObj (QUOTE rows))) (fontSpec (FONTCREATE (COND ((EQIO.EqnProperty eqnObj (QUOTE fontSpec))) (T DEFAULTFONT)) NIL NIL NIL imageStream)) layoutBox boxList colData rowData colGap rowGap shift) (* * set quantities that define layout) (SETQ shift (IQUOTIENT (FONTPROP fontSpec (QUOTE ASCENT)) 2)) (SETQ colGap (STRINGWIDTH " " fontSpec)) (SETQ rowGap colGap) (* * determine overall box) (COND ((OR (ILEQ columns 0) (ILEQ rows 0)) (SETQ layoutBox (create IMAGEBOX XSIZE ← 0 YSIZE ← 0))) (T (SETQ boxList (for piece in (EQIO.EqnDataList eqnObj) collect (FS.Box piece imageStream))) (SETQ colData (ARRAY columns (QUOTE FIXP) 0)) (SETQ rowData (ARRAY rows)) (for row from 1 to rows bind (boxes ← boxList) rAscent rDesc do (SETQ rAscent 0) (SETQ rDesc 0) (for col from 1 to columns bind b do (SETQ b (CAR boxes)) (SETQ boxes (CDR boxes)) (SETQ rAscent (MAX rAscent (DIFFERENCE (fetch YSIZE of b) (fetch YDESC of b)))) (SETQ rDesc (MAX rDesc (fetch YDESC of b))) (SETA colData col (MAX (ELT colData col) (fetch XSIZE of b)))) (SETA rowData row (CONS (PLUS rAscent rDesc) rDesc))) (SETQ layoutBox (create IMAGEBOX XSIZE ←(PLUS (for col from 1 to columns sum (ELT colData col)) (TIMES (SUB1 columns) colGap)) YSIZE ←(PLUS (for row from 1 to rows sum (CAR (ELT rowData row))) (TIMES (SUB1 rows) rowGap)))))) (replace YDESC of layoutBox with (DIFFERENCE (IQUOTIENT (fetch YSIZE of layoutBox) 2) shift)) (replace XKERN of layoutBox with 0) (* * return overall box and individual positions of all the parts) (LET ((xLow 0) (yHigh (fetch YSIZE of layoutBox)) (colPos (ARRAY columns (QUOTE FIXP)))) (* (xLow,yHigh) is position of upper left corner of block of matrix parts) (COND ((IGREATERP columns 0) (* set colPos to horizontal position of left edge of each column) (SETA colPos 1 xLow) (for col from 2 to columns do (SETA colPos col (PLUS (ELT colPos (SUB1 col)) colGap (ELT colData (SUB1 col)))) ))) (EQIO.MakeSpec layoutBox (COND ((AND (IGREATERP columns 0) (IGREATERP rows 0)) (for row from 1 to rows bind rowValue (boxes ← boxList) (rowPos ←(PLUS yHigh rowGap) ) join (SETQ rowPos (DIFFERENCE rowPos (PLUS rowGap (CAR (SETQ rowValue (ELT rowData row)))))) (* rowPos is vertical position of bottom of row) (for col from 1 to columns bind b collect (SETQ b (CAR boxes)) (SETQ boxes (CDR boxes)) (EQIO.MakeDataSpec (create POSITION XCOORD ←(PLUS (ELT colPos col) (IQUOTIENT (DIFFERENCE (ELT colData col) (fetch XSIZE of b)) 2)) YCOORD ←(PLUS rowPos (CDR rowValue))) )))) (T (* no pieces in this layout) NIL))))))) (EQ.MatrixAdd (LAMBDA (eqnObj which place window) (* thh: " 3-Jun-85 10:19") (* adds new row/column to matrix) (* currently copies lists when adding new data instead of modifying the original lists) (PROG ((rows (EQIO.EqnProperty eqnObj (QUOTE rows))) (columns (EQIO.EqnProperty eqnObj (QUOTE columns))) (dataList (EQIO.EqnDataList eqnObj)) newData tempData firstPiece continueFlg) (SELECTQ which (row (SETQ newData (EQN.DefaultData (EQIO.EqnType eqnObj) (EQIO.EqnProperty eqnObj (QUOTE fontSpec)) columns)) (* insert newData after the place*columns piece) (SETQ tempData (for d in dataList as i from 1 to (TIMES place columns) collect (SETQ dataList (CDR dataList)) d)) (EQIO.SetDataList eqnObj (APPEND tempData newData dataList)) (add rows 1) (EQIO.EqnProperty eqnObj (QUOTE rows) rows) (SETQ firstPiece (ADD1 (TIMES columns place))) (SETQ continueFlg (CONS 1 (TIMES columns (ADD1 place))))) (column (SETQ newData (EQN.DefaultData (EQIO.EqnType eqnObj) (EQIO.EqnProperty eqnObj (QUOTE fontSpec)) rows)) (EQIO.SetDataList eqnObj (for i from 1 to rows bind newD join (SETQ newD (CAR newData)) (SETQ newData (CDR newData)) (APPEND (for j from 1 to place bind d collect (SETQ d (CAR dataList) ) (SETQ dataList (CDR dataList) ) d) (LIST newD) (for j from (ADD1 place) to columns bind d collect (SETQ d (CAR dataList) ) (SETQ dataList (CDR dataList) ) d)))) (add columns 1) (EQIO.EqnProperty eqnObj (QUOTE columns) columns) (SETQ firstPiece (ADD1 place)) (SETQ continueFlg (LIST columns))) (ERROR "EQ.MatrixAdd: invalid arg for which = " which)) (EQIO.NumPieces eqnObj (TIMES rows columns)) (EQN.StartEdit eqnObj window firstPiece continueFlg (QUOTE PENDINGDEL))))) (EQ.MatrixChanged (LAMBDA (eqnObj) (* thh: "31-May-85 14:21") (* called when number of pieces in matrix changed) (EQIO.EqnProperty eqnObj (QUOTE rowMenu) NIL) (EQIO.EqnProperty eqnObj (QUOTE colMenu) NIL))) (EQ.MatrixCreate (LAMBDA NIL (* THH "12-Jul-85 10:04") (* allows user to specify initial number of rows and columns in a new matrix) (LET (rows columns numPieces retry) (repeatwhile (GREATERP numPieces EQ.Matrix.MaxPieces) do (COND (retry (CLRPROMPT) (PROMPTPRINT "Too many matrix elements: " numPieces " [max allowed is " EQ.Matrix.MaxPieces "]"))) (SETQ rows (MAX (RNUMBER "How many rows for matrix?") 0)) (SETQ columns (MAX (RNUMBER "How many columns for matrix?") 0)) (SETQ numPieces (TIMES rows columns)) (SETQ retry T)) (LIST (QUOTE numPieces) numPieces (QUOTE rows) rows (QUOTE columns) columns)))) (EQ.MatrixDelete (LAMBDA (eqnObj which place) (* thh: " 3-Jun-85 11:56") (* deletes row/column from matrix) (COND ((IGREATERP place 0) (PROG ((rows (EQIO.EqnProperty eqnObj (QUOTE rows))) (columns (EQIO.EqnProperty eqnObj (QUOTE columns))) (dataList (EQIO.EqnDataList eqnObj))) (SELECTQ which (row (EQIO.SetDataList eqnObj (for d in dataList as i from 1 bind (start ←(TIMES (SUB1 place) columns)) (stop ←(TIMES place columns)) collect d unless (AND (IGREATERP i start) (ILEQ i stop)))) (add rows -1) (EQIO.EqnProperty eqnObj (QUOTE rows) rows)) (column (EQIO.SetDataList eqnObj (for d in dataList bind (j ← 0) eachtime (COND ((IGEQ j columns) (SETQ j 0))) (add j 1) collect d unless (IEQP j place) )) (add columns -1) (EQIO.EqnProperty eqnObj (QUOTE columns) columns)) (ERROR "EQ.MatrixDelete: invalid arg for which = " which)) (EQIO.NumPieces eqnObj (TIMES rows columns))))))) (EQ.MatrixEdit (LAMBDA (eqnObj window button) (* THH "12-Jul-85 10:08") (* adds and removes rows and columns from matrix) (* returns non-NIL if eqnObj modified) (COND ((EQ (EQIO.EqnType eqnObj) (QUOTE matrix)) (LET ((editMenu (EQIO.TypeProp (QUOTE matrix) (QUOTE editMenu))) action place) (COND ((NOT (type? MENU editMenu)) (SETQ editMenu (create MENU CENTERFLG ← T ITEMS ←(QUOTE (("add before col" (QUOTE beforeCol)) ("add before row" (QUOTE beforeRow)) ("add after col" (QUOTE afterCol)) ("add after row" (QUOTE afterRow)) ("DELETE column" (QUOTE delCol)) ("DELETE row" (QUOTE delRow)) ("[change enclosure]" (QUOTE enclosure))))) ) (EQIO.TypeProp (QUOTE matrix) (QUOTE editMenu) editMenu))) (SETQ action (MENU editMenu)) (COND ((EQ action (QUOTE enclosure)) (EQ.EnclosureEdit eqnObj)) (T (* edit layout) (SETQ place (SELECTQ action ((beforeCol afterCol delCol) (COND ((IGREATERP (EQIO.EqnProperty eqnObj (QUOTE columns)) 0) (MENU (EQ.MatrixGetMenu eqnObj (QUOTE column))) ) ((EQ action (QUOTE beforeCol)) 1) (T 0))) ((beforeRow afterRow delRow) (COND ((IGREATERP (EQIO.EqnProperty eqnObj (QUOTE rows)) 0) (MENU (EQ.MatrixGetMenu eqnObj (QUOTE row)))) ((EQ action (QUOTE beforeRow)) 1) (T 0))) NIL)) (COND (place (COND ((EQ action (QUOTE beforeCol)) (add place -1) (SETQ action (QUOTE afterCol))) ((EQ action (QUOTE beforeRow)) (add place -1) (SETQ action (QUOTE afterRow)))) (SELECTQ action (afterCol (EQ.MatrixAdd eqnObj (QUOTE column) place window) T) (afterRow (EQ.MatrixAdd eqnObj (QUOTE row) place window) T) (delCol (EQ.MatrixDelete eqnObj (QUOTE column) place) T) (delRow (EQ.MatrixDelete eqnObj (QUOTE row) place) T) NIL))))))) (T (* eqnObj not a matrix) NIL)))) (EQ.MatrixGetMenu (LAMBDA (eqnObj which) (* thh: " 3-Jun-85 09:35") (* gets menu for eqnObj, which is either row or column) (SELECTQ which (row (PROG ((rowMenu (EQIO.EqnProperty eqnObj (QUOTE rowMenu)))) (COND ((NOT (type? MENU rowMenu)) (SETQ rowMenu (create MENU TITLE ← "row #" ITEMS ←(for i from 1 to (EQIO.EqnProperty eqnObj (QUOTE rows)) collect i))) (EQIO.EqnProperty eqnObj (QUOTE rowMenu) rowMenu))) (RETURN rowMenu))) (column (PROG ((colMenu (EQIO.EqnProperty eqnObj (QUOTE colMenu)))) (COND ((NOT (type? MENU colMenu)) (SETQ colMenu (create MENU TITLE ← "col #" MENUROWS ← 1 ITEMS ←(for i from 1 to (EQIO.EqnProperty eqnObj (QUOTE columns)) collect i))) (EQIO.EqnProperty eqnObj (QUOTE colMenu) colMenu))) (RETURN colMenu))) NIL))) (EQ.MatrixSelect (LAMBDA (eqnObj) (* thh: " 3-Jun-85 09:20") (* selects piece to edit by row and column number) (COND ((EQ (EQIO.EqnType eqnObj) (QUOTE matrix)) (PROG (row col) (COND ((IGREATERP (EQIO.NumPieces eqnObj) 0) (SETQ row (MENU (EQ.MatrixGetMenu eqnObj (QUOTE row)))) (COND (row (SETQ col (MENU (EQ.MatrixGetMenu eqnObj (QUOTE column)))) (COND (col (RETURN (PLUS (TIMES (EQIO.EqnProperty eqnObj (QUOTE columns)) (SUB1 row)) col)))))))))) (T (* eqnObj is not a matrix) NIL)))) ) (RPAQ? EQ.Matrix.MaxPieces 100) (DECLARE: DOEVAL@COMPILE DONTCOPY (GLOBALVARS EQ.Matrix.MaxPieces) ) (EQIO.AddType (QUOTE matrix) (QUOTE EQ.Matrix) 1 (QUOTE (objectProps (rows 1 columns 1 enclosureKind NIL enclosureSide NIL) variable? T wholeEditFn EQ.MatrixEdit specialSelectFn EQ.MatrixSelect initialPropFn EQ.MatrixCreate changeFn EQ.MatrixChanged))) (* * EQNFORMS module: Part 4 of 5) (* fraction) (DEFINEQ (EQ.Fraction (LAMBDA (eqnObj imageStream draw?) (* THH "21-May-85 12:14") (* form function for fraction) (* fraction defined by shift -- distance of line above base, gap -- space above and below the line, width -- width of the line and extend -- extra length of line on either side) (* these parameters could be specified by props to allow user to change them) (PROG ((size (EQ.StreamSize imageStream)) shift gap width extend nBox dBox pos box pNumer pDenom) (SETQ shift (IQUOTIENT (FONTPROP (FONTCREATE (COND ((EQIO.EqnProperty eqnObj (QUOTE fontSpec))) (T DEFAULTFONT)) NIL NIL NIL imageStream) (QUOTE ASCENT)) 2)) (SETQ gap size) (SETQ width size) (SETQ extend size) (SETQ nBox (FS.Box (EQIO.EqnData eqnObj 1) imageStream)) (SETQ dBox (FS.Box (EQIO.EqnData eqnObj 2) imageStream)) (SETQ pos (PLUS (fetch YSIZE of dBox) (TIMES 2 gap) width)) (* pos is distance from bottom of box to bottom of numerator) (SETQ box (create IMAGEBOX XSIZE ←(PLUS (MAX (fetch XSIZE of nBox) (fetch XSIZE of dBox)) (TIMES 2 extend)) YSIZE ←(PLUS (fetch YSIZE of nBox) pos) YDESC ←(PLUS gap (fetch YSIZE of dBox) (MINUS shift)) XKERN ← 0)) (SETQ pNumer (create POSITION XCOORD ←(IQUOTIENT (DIFFERENCE (fetch XSIZE of box) (fetch XSIZE of nBox)) 2) YCOORD ←(PLUS pos (fetch YDESC of nBox)))) (SETQ pDenom (create POSITION XCOORD ←(IQUOTIENT (DIFFERENCE (fetch XSIZE of box) (fetch XSIZE of dBox)) 2) YCOORD ←(fetch YDESC of dBox))) (COND (draw? (* note that original x,y pos not preserved) (RELMOVETO 0 shift imageStream) (RELDRAWTO (fetch XSIZE of box) 0 width NIL imageStream))) (RETURN (EQIO.MakeSpec box (LIST (EQIO.MakeDataSpec pNumer (create REGION LEFT ← 0 BOTTOM ← pos WIDTH ←(fetch XSIZE of box) HEIGHT ←(fetch YSIZE of nBox))) (EQIO.MakeDataSpec pDenom (create REGION LEFT ← 0 BOTTOM ← 0 WIDTH ←(fetch XSIZE of box) HEIGHT ←(fetch YSIZE of dBox)))) )) (* selection region for numerator (denominator) is entire top (bottom) half of fraction) ))) (EQ.Make.fraction (LAMBDA (numerator denominator fontSpec) (* thh: " 9-Jan-86 10:14") (EQN.Make (QUOTE fraction) (LIST numerator denominator) fontSpec))) ) (* * sum group) (DEFINEQ (EQ.SumGroup (LAMBDA (eqnObj imageStream draw?) (* thh: "30-Apr-87 10:16") (* form function for forms drawn like a summation) (* form defined by gap -- distance between symbol and index (below) and limits (above), and vGap -- distance between symbol and value) (PROG ((size (EQ.StreamSize imageStream)) (char (LIST (COND ((EQ.UseNS? imageStream) (FS.MakeItem (QUOTE (Modern 30)) (MKSTRING (CHARACTER (SELECTQ (EQIO.EqnType eqnObj) (sum 61306) (product 61307) (union 61271) (intersection 61270) (SHOULDNT "eqn not a known sum group"))))) ) (T (* use press fonts) (FS.MakeItem (QUOTE (Sigma 20)) (SELECTQ (EQIO.EqnType eqnObj) (sum (QUOTE "M")) (product (QUOTE "P")) (union (QUOTE "U")) (intersection (QUOTE "I")) (SHOULDNT "eqn not a known sum group"))))) )) extraShift charBox indexBox limitBox valueBox indexRegion limitRegion valueRegion charRegion boxRegion box temp gap vGap) (SETQ gap size) (SETQ vGap (TIMES 2 size)) (* extraShift compensates for extra space around the NS chars) (SETQ extraShift (COND ((EQ.UseNS? imageStream) (TIMES 4 size)) (T 0))) (SETQ charBox (FS.Box char imageStream)) (SETQ indexBox (FS.Box (EQIO.EqnData eqnObj 1) imageStream)) (SETQ limitBox (FS.Box (EQIO.EqnData eqnObj 2) imageStream)) (SETQ valueBox (FS.Box (EQIO.EqnData eqnObj 3) imageStream)) (SETQ temp (AB.PositionRegion charBox NIL (QUOTE bottom) (QUOTE center) indexBox (QUOTE center) (DIFFERENCE gap extraShift) 0 size)) (SETQ indexRegion (CAR temp)) (SETQ temp (AB.PositionRegion charBox temp (QUOTE top) (QUOTE center) limitBox (QUOTE center) (TIMES -2 gap) 0 size)) (* -2*gap used instead of gap since symbol doesn't fill its box) (SETQ limitRegion (CAR temp)) (SETQ temp (AB.PositionRegion charBox temp (QUOTE right) (QUOTE display) valueBox (QUOTE display) vGap extraShift size)) (SETQ valueRegion (CAR temp)) (SETQ charRegion (AB.BoxToRegion charBox 0 0)) (SETQ boxRegion (UNIONREGIONS charRegion indexRegion limitRegion valueRegion)) (SETQ box (AB.RegionToBox boxRegion (PLUS (fetch YDESC of charBox) extraShift))) (COND (draw? (* note that original x, y position not preserved) (RELMOVETO (MINUS (fetch LEFT of boxRegion)) (MINUS extraShift) imageStream) (FS.Display char imageStream))) (RETURN (EQIO.MakeSpec box (LIST (EQIO.MakeDataSpec (AB.RelativePos indexRegion boxRegion (fetch YDESC of indexBox))) (EQIO.MakeDataSpec (AB.RelativePos limitRegion boxRegion (fetch YDESC of limitBox))) (EQIO.MakeDataSpec (AB.RelativePos valueRegion boxRegion (fetch YDESC of valueBox))))))))) (EQ.Make.sum (LAMBDA (lowerIndex upperLimit summand fontSpec) (* thh: " 9-Jan-86 10:16") (EQN.Make (QUOTE sum) (LIST lowerIndex upperLimit summand) fontSpec))) (EQ.Make.product (LAMBDA (lowerIndex upperLimit factor fontSpec) (* thh: " 9-Jan-86 10:17") (EQN.Make (QUOTE product) (LIST lowerIndex upperLimit factor) fontSpec))) (EQ.Make.union (LAMBDA (lowerIndex upperLimit set fontSpec) (* thh: " 9-Jan-86 10:18") (EQN.Make (QUOTE union) (LIST lowerIndex upperLimit set) fontSpec))) (EQ.Make.intersection (LAMBDA (lowerIndex upperLimit set fontSpec) (* thh: " 9-Jan-86 10:18") (EQN.Make (QUOTE intersection) (LIST lowerIndex upperLimit set) fontSpec))) ) (* * integral group) (DEFINEQ (EQ.IntegralGroup (LAMBDA (eqnObj imageStream draw?) (* thh: "30-Apr-87 09:36") (* form function for forms drawn like an integral) (* form defined by gap -- distance between symbol and limits and vGap -- distance between symbol and value) (PROG ((size (EQ.StreamSize imageStream)) (char (LIST (COND ((EQ.UseNS? imageStream) (FS.MakeItem (QUOTE (Modern 30)) (MKSTRING (CHARACTER (SELECTQ (EQIO.EqnType eqnObj) (integral 61301) (lineIntegral 61302) (SHOULDNT "eqn not a known integral group"))))) ) (T (* use press fonts) (FS.MakeItem (QUOTE (Sigma 20)) (SELECTQ (EQIO.EqnType eqnObj) (integral (QUOTE "S")) (lineIntegral (QUOTE "C")) (SHOULDNT "eqn not a known integral group"))))) )) charBox lowerBox upperBox valueBox lowerRegion upperRegion valueRegion charRegion boxRegion box temp gap vGap) (SETQ gap size) (SETQ vGap (TIMES 5 size)) (SETQ charBox (FS.Box char imageStream)) (SETQ lowerBox (FS.Box (EQIO.EqnData eqnObj 1) imageStream)) (SETQ upperBox (FS.Box (EQIO.EqnData eqnObj 2) imageStream)) (SETQ valueBox (FS.Box (EQIO.EqnData eqnObj 3) imageStream)) (SETQ temp (AB.Position2Regions charBox NIL (QUOTE right) upperBox (QUOTE center) lowerBox (QUOTE center) (MINUS gap) (TIMES -6 gap) 0 0 size)) (* negative gaps since symbol doesn't fill its box) (SETQ upperRegion (CAR temp)) (SETQ lowerRegion (CADR temp)) (SETQ temp (AB.PositionRegion charBox temp (QUOTE right) (QUOTE display) valueBox (QUOTE display) vGap 0 size)) (SETQ valueRegion (CAR temp)) (SETQ charRegion (AB.BoxToRegion charBox 0 0)) (SETQ boxRegion (UNIONREGIONS charRegion upperRegion lowerRegion valueRegion)) (SETQ box (AB.RegionToBox boxRegion (fetch YDESC of charBox))) (COND (draw? (* note that original x, y position not preserved) (RELMOVETO (MINUS (fetch LEFT of boxRegion)) 0 imageStream) (FS.Display char imageStream))) (RETURN (EQIO.MakeSpec box (LIST (EQIO.MakeDataSpec (AB.RelativePos lowerRegion boxRegion (fetch YDESC of lowerBox))) (EQIO.MakeDataSpec (AB.RelativePos upperRegion boxRegion (fetch YDESC of upperBox))) (EQIO.MakeDataSpec (AB.RelativePos valueRegion boxRegion (fetch YDESC of valueBox))))))))) (EQ.Make.integral (LAMBDA (lowerLimit upperLimit integrand fontSpec) (* thh: " 9-Jan-86 10:19") (EQN.Make (QUOTE integral) (LIST lowerLimit upperLimit integrand) fontSpec))) (EQ.Make.lineIntegral (LAMBDA (lowerLimit upperLimit integrand fontSpec) (* thh: " 9-Jan-86 10:20") (EQN.Make (QUOTE lineIntegral) (LIST lowerLimit upperLimit integrand) fontSpec))) ) (* * super- and sub- scripts) (DEFINEQ (EQ.Script (LAMBDA (eqnObj imageStream draw?) (* THH "23-May-85 14:07") (* form function for forms with sub and superscripts) (* form defined by gap -- horizontal distance between main symbol and sub/superscripts, , and shift -- vertical distance of centers of sub/superscripts below/above corner of main symbol) (PROG ((size (EQ.StreamSize imageStream)) mainBox super1Box sub1Box super2Box sub2Box super1Region sub1Region super2Region sub2Region mainRegion boxRegion box temp gap shift) (SETQ gap size) (SETQ shift size) (SETQ mainBox (FS.Box (EQIO.EqnData eqnObj 1) imageStream)) (SETQ sub1Box (FS.Box (EQIO.EqnData eqnObj 2) imageStream)) (SETQ super1Box (FS.Box (EQIO.EqnData eqnObj 3) imageStream)) (SETQ sub2Box (FS.Box (EQIO.EqnData eqnObj 4) imageStream)) (SETQ super2Box (FS.Box (EQIO.EqnData eqnObj 5) imageStream)) (SETQ temp (AB.Position2Regions mainBox NIL (QUOTE right) super1Box (QUOTE center) sub1Box (QUOTE center) gap gap shift (MINUS shift) size)) (SETQ super1Region (CAR temp)) (SETQ sub1Region (CADR temp)) (SETQ temp (AB.Position2Regions mainBox (CADDR temp) (QUOTE left) super2Box (QUOTE center) sub2Box (QUOTE center) gap gap shift (MINUS shift) size)) (SETQ super2Region (CAR temp)) (SETQ sub2Region (CADR temp)) (SETQ mainRegion (AB.BoxToRegion mainBox 0 0)) (SETQ boxRegion (UNIONREGIONS mainRegion super1Region sub1Region super2Region sub2Region)) (SETQ box (AB.RegionToBox boxRegion (fetch YDESC of mainBox))) (* * this form has nothing extra to draw) (RETURN (EQIO.MakeSpec box (LIST (EQIO.MakeDataSpec (AB.RelativePos mainRegion boxRegion (fetch YDESC of mainBox))) (EQIO.MakeDataSpec (AB.RelativePos sub1Region boxRegion (fetch YDESC of sub1Box))) (EQIO.MakeDataSpec (AB.RelativePos super1Region boxRegion (fetch YDESC of super1Box))) (EQIO.MakeDataSpec (AB.RelativePos sub2Region boxRegion (fetch YDESC of sub2Box))) (EQIO.MakeDataSpec (AB.RelativePos super2Region boxRegion (fetch YDESC of super2Box))))))))) (EQ.Make.sub/superscripts (LAMBDA (mainValue lowerRight upperRight lowerLeft upperLeft fontSpec) (* thh: " 9-Jan-86 10:21") (EQN.Make (QUOTE sub/superscripts) (LIST mainValue lowerRight upperRight lowerLeft upperLeft) fontSpec))) ) (* * max/min/limit etc) (DEFINEQ (EQ.MaxMin (LAMBDA (eqnObj imageStream draw?) (* thh: " 9-Jan-86 10:02") (* form function for max/min/limit etc) (PROG ((size (EQ.StreamSize imageStream)) functionBox indexBox valueBox box functionRegion indexRegion valueRegion boxRegion gap vGap temp) (SETQ gap (TIMES 2 size)) (SETQ vGap size) (SETQ functionBox (FS.Box (EQIO.EqnData eqnObj 1) imageStream)) (SETQ indexBox (FS.Box (EQIO.EqnData eqnObj 2) imageStream)) (SETQ valueBox (FS.Box (EQIO.EqnData eqnObj 3) imageStream)) (SETQ temp (AB.PositionRegion functionBox NIL (QUOTE bottom) (QUOTE center) indexBox (QUOTE center) vGap 0 size)) (SETQ indexRegion (CAR temp)) (SETQ temp (AB.PositionRegion functionBox temp (QUOTE right) (QUOTE display) valueBox (QUOTE display) gap 0 size)) (SETQ valueRegion (CAR temp)) (SETQ functionRegion (AB.BoxToRegion functionBox 0 0)) (SETQ boxRegion (UNIONREGIONS functionRegion indexRegion valueRegion)) (SETQ box (AB.RegionToBox boxRegion (fetch YDESC of functionBox))) (* * nothing extra to draw) (RETURN (EQIO.MakeSpec box (LIST (EQIO.MakeDataSpec (AB.RelativePos functionRegion boxRegion (fetch YDESC of functionBox))) (EQIO.MakeDataSpec (AB.RelativePos indexRegion boxRegion (fetch YDESC of indexBox))) (EQIO.MakeDataSpec (AB.RelativePos valueRegion boxRegion (fetch YDESC of valueBox))))))))) (EQ.Make.max/min (LAMBDA (function index value fontSpec) (* thh: " 9-Jan-86 10:21") (EQN.Make (QUOTE max/min) (LIST function index value) fontSpec))) ) (* * utilities) (DEFINEQ (EQ.StreamSize (LAMBDA (imageStream) (* thh: " 3-May-85 08:37") (* standard size factor for the stream) (MAX 1 (IQUOTIENT (STRINGWIDTH "A" (FONTCREATE DEFAULTFONT NIL NIL NIL imageStream)) 5)))) (EQ.UseNS? (LAMBDA (imageStream) (* thh: " 9-Jan-86 10:29") (* * returns non-NIL if NS characters should be used for special symbols on imageStream) (SELECTQ (IMAGESTREAMTYPE imageStream) (DISPLAY EQ.UseNSChars) (PRESS NIL) (INTERPRESS T) EQ.UseNSChars))) ) (DECLARE: DOEVAL@COMPILE DONTCOPY (GLOBALVARS EQ.UseNSChars) ) (* EQ.UseNSChars = NIL to use press fonts for display) (RPAQ? EQ.UseNSChars NIL) (EQIO.AddType (QUOTE fraction) (QUOTE EQ.Fraction) 2 (QUOTE (pieceNames ("numerator" "denominator")))) (EQIO.AddType (QUOTE sum) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "summand")))) (EQIO.AddType (QUOTE product) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "factor")))) (EQIO.AddType (QUOTE union) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "set")))) (EQIO.AddType (QUOTE intersection) (QUOTE EQ.SumGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("index" "limit" "set")))) (EQIO.AddType (QUOTE integral) (QUOTE EQ.IntegralGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("lower limit" "upper limit" "integrand")))) (EQIO.AddType (QUOTE lineIntegral) (QUOTE EQ.IntegralGroup) 3 (QUOTE (initialData (-2 -2 0) pieceNames ("lower limit" "upper limit" "integrand") menuLabel "line integral"))) (EQIO.AddType (QUOTE sub/superscripts) (QUOTE EQ.Script) 5 (QUOTE (initialData (0 -1 -1 -1 -1) pieceNames ("main value" "right subscript" "right superscript" "left subscript" "left superscript")))) (EQIO.AddType (QUOTE max/min) (QUOTE EQ.MaxMin) 3 (QUOTE (initialData (0 -2 0) pieceNames ("function" "index" "value") menuLabel "max min limit"))) (* * EQROOT module: Part 5 of 5) (DEFINEQ (EQ.Root (LAMBDA (eqnObj imageStream draw?) (* thh: "18-Mar-86 14:47") (* form function for roots) (* layout defined by vGap -- extra vertical space on either side of radicand, gap -- extra horizontal space on either side of radicand, ivGap -- vertical space between index and radical sign, igap -- extra horizontal extent of sign around index) (PROG ((size (EQ.StreamSize imageStream)) rBox iBox gap vGap ivGap igap baseLen barLen height rise desc toBottomLen toTopLen width box) (SETQ gap (TIMES 2 size)) (SETQ vGap (TIMES 2 size)) (SETQ ivGap size) (SETQ igap 0) (SETQ width size) (SETQ rBox (FS.Box (EQIO.EqnData eqnObj 1) imageStream)) (SETQ iBox (FS.Box (EQIO.EqnData eqnObj 2) imageStream)) (* * determine size of parts of radical sign and draw it if requested) (SETQ baseLen (MAX (TIMES 4 size) (PLUS (TIMES 2 igap) (fetch XSIZE of iBox)))) (SETQ barLen (PLUS (TIMES 2 gap) (fetch XSIZE of rBox))) (SETQ height (PLUS (TIMES 2 vGap) (fetch YSIZE of rBox) (QUOTIENT width 2))) (SETQ rise (QUOTIENT height 2)) (SETQ desc (PLUS (fetch YDESC of rBox) vGap)) (SETQ toBottomLen (TIMES 2 size)) (SETQ toTopLen (TIMES 4 toBottomLen)) (COND (draw? (EQ.DrawRadicalSign height rise desc baseLen toBottomLen toTopLen barLen width imageStream))) (* * get size and position values) (SETQ box (create IMAGEBOX XSIZE ←(PLUS baseLen toBottomLen toTopLen barLen) YSIZE ←(MAX (PLUS height (DIFFERENCE width (QUOTIENT width 2))) (PLUS rise ivGap (fetch YSIZE of iBox))) YDESC ← desc XKERN ← 0)) (RETURN (EQIO.MakeSpec box (LIST (EQIO.MakeDataSpec (create POSITION XCOORD ←(PLUS baseLen toBottomLen toTopLen gap) YCOORD ← desc)) (EQIO.MakeDataSpec (create POSITION XCOORD ←(QUOTIENT (DIFFERENCE baseLen (fetch XSIZE of iBox)) 2) YCOORD ←(PLUS rise ivGap (fetch YDESC of iBox)))))))))) (EQ.Make.root (LAMBDA (radicand index fontSpec) (* thh: " 9-Jan-86 10:22") (EQN.Make (QUOTE root) (LIST radicand index) fontSpec))) ) (DEFINEQ (EQ.DrawRadicalSign (LAMBDA (height rise desc baseLen toBottomLen toTopLen barLen width imageStream) (* thh: "28-Jun-85 13:04") (* draws specified radical sign on imageStream) (RELMOVETO 0 (DIFFERENCE rise desc) imageStream) (RELDRAWTO baseLen 0 width NIL imageStream) (RELDRAWTO toBottomLen (MINUS rise) (TIMES 2 width) NIL imageStream) (RELDRAWTO toTopLen height width NIL imageStream) (RELDRAWTO barLen 0 width NIL imageStream))) ) (EQIO.AddType (QUOTE root) (QUOTE EQ.Root) 2 (QUOTE (pieceNames ("radicand" "index") initialData (0 -1)))) (PUTPROPS EQUATIONFORMS COPYRIGHT ("Xerox Corporation" 1986 1987)) (DECLARE: DONTCOPY (FILEMAP (NIL (6657 20458 (AB.RealPosition 6667 . 7627) (AB.PointPos 7629 . 8816) (AB.SidePosition 8818 . 9761) (AB.PlaceRegion 9763 . 11019) (AB.AdjustToLL 11021 . 11712) (AB.OppositeSide 11714 . 11994) (AB.RegionToBox 11996 . 12605) (AB.BoxToRegion 12607 . 13237) (AB.RelativePos 13239 . 13774) ( AB.BiggerRegion 13776 . 14530) (AB.Check 14532 . 16221) (AB.PositionRegion 16223 . 17123) ( AB.Position2Regions 17125 . 20456)) (20536 21622 (EQ.Group 20546 . 21192) (EQ.GroupCreate 21194 . 21338) (EQ.Make.group 21340 . 21620)) (21992 22930 (EQ.AddEnclosure 22002 . 22713) ( EQ.GetEnclosureData 22715 . 22928)) (23486 28334 (EQ.enclosure 23496 . 24786) (EQ.EnclosureCreate 24788 . 25472) (EQ.EnclosureEdit 25474 . 26664) (EQ.EnclosureKind 26666 . 27717) (EQ.EnclosureSide 27719 . 28332)) (28372 35191 (EQ.angles 28382 . 29547) (EQ.bars 29549 . 30529) (EQ.braces 30531 . 31886) (EQ.brackets 31888 . 33026) (EQ.parentheses 33028 . 34259) (EQ.enclosureForm 34261 . 35026) ( EQ.enclosureWidth 35028 . 35189)) (35232 44285 (EQ.DrawAngles 35242 . 36812) (EQ.DrawBars 36814 . 37879) (EQ.DrawBraces 37881 . 40871) (EQ.DrawBrackets 40873 . 42511) (EQ.DrawParentheses 42513 . 44283 )) (44365 61642 (EQ.Matrix 44375 . 45655) (EQ.Make.matrix 45657 . 46298) (EQ.layout 46300 . 51119) ( EQ.MatrixAdd 51121 . 53964) (EQ.MatrixChanged 53966 . 54319) (EQ.MatrixCreate 54321 . 55226) ( EQ.MatrixDelete 55228 . 56655) (EQ.MatrixEdit 56657 . 59489) (EQ.MatrixGetMenu 59491 . 60773) ( EQ.MatrixSelect 60775 . 61640)) (62106 65469 (EQ.Fraction 62116 . 65264) (EQ.Make.fraction 65266 . 65467)) (65492 70145 (EQ.SumGroup 65502 . 69318) (EQ.Make.sum 69320 . 69519) (EQ.Make.product 69521 . 69727) (EQ.Make.union 69729 . 69928) (EQ.Make.intersection 69930 . 70143)) (70173 73857 ( EQ.IntegralGroup 70183 . 73421) (EQ.Make.integral 73423 . 73634) (EQ.Make.lineIntegral 73636 . 73855)) (73894 77043 (EQ.Script 73904 . 76719) (EQ.Make.sub/superscripts 76721 . 77041)) (77074 79222 ( EQ.MaxMin 77084 . 79020) (EQ.Make.max/min 79022 . 79220)) (79245 79953 (EQ.StreamSize 79255 . 79586) ( EQ.UseNS? 79588 . 79951)) (81714 84541 (EQ.Root 81724 . 84351) (EQ.Make.root 84353 . 84539)) (84542 85183 (EQ.DrawRadicalSign 84552 . 85181))))) STOP