DIRECTORY Graphics USING[Context, Path, NewPath, LineTo, MoveTo, DrawTo, SetCP, SetStipple, DrawStroke, DrawArea], IPConstants, Misc; MiscImpl: CEDAR PROGRAM IMPORTS Graphics EXPORTS Misc = BEGIN OPEN Misc; WindCreate: PUBLIC PROC[min, max: INT] RETURNS [Window]={ RETURN [NEW[WindowRep_[span: IntlCreate[min, max], curtains: NIL]]]};-- WindCreate-- WindAddCurtain: PUBLIC PROC[w: Window, curtain: Interval]={ newCurtainHd, newCurtainTl: LIST OF Interval; IF curtain = NIL THEN RETURN; newCurtainHd _ newCurtainTl _ CONS[NIL, NIL]; FOR c: LIST OF Interval _ w.curtains, c.rest UNTIL c = NIL DO IF IntlIntersect[curtain, c.first] # NIL OR (c.first.max + 1 = curtain.min) OR (curtain.max + 1 = c.first.min) THEN {curtain _ IntlMakeBIntl[curtain, c.first]; LOOP}; IF c.first.max < curtain.min THEN { newCurtainTl.rest _ CONS[c.first, NIL]; newCurtainTl _ newCurtainTl.rest; LOOP}; IF c.first.min > curtain.max THEN { newCurtainTl.rest _ CONS[curtain, c]; EXIT}; REPEAT FINISHED => {newCurtainTl.rest _ LIST[curtain]} ENDLOOP; w.curtains _ newCurtainHd.rest; };-- WindAddCurtain-- WindIsCovered: PUBLIC PROC[w: Window] RETURNS [BOOL]={ IF w.curtains = NIL THEN RETURN [w.span = NIL]; FOR c: LIST OF Interval _ w.curtains, c.rest UNTIL c = NIL DO IF IntlIntersect[c.first, w.span] # NIL THEN RETURN [IntlContainp[c.first, w.span]] ENDLOOP; RETURN [FALSE] };--WindIsCovered -- WindPassesIntl: PUBLIC PROC[w: Window, intl: Interval] RETURNS [BOOL]={ IF NOT IntlContainp[w.span, intl] THEN RETURN [FALSE]; FOR c: LIST OF Interval _ w.curtains, c.rest UNTIL c = NIL DO IF IntlIntersect[c.first, intl] # NIL THEN RETURN [FALSE] ENDLOOP; RETURN [TRUE]};-- WindPassesIntl-- WindCurtainsCoverIntl: PUBLIC PROC[w: Window, intl: Interval] RETURNS [BOOL] ={ FOR c: LIST OF Interval _ w.curtains, c.rest UNTIL c = NIL DO IF IntlIntersect[c.first, intl] # NIL THEN RETURN [IntlContainp[c.first, intl]] ENDLOOP; RETURN [FALSE] };--WindCurtainCoversIntl-- RectSubtractFailure: PUBLIC ERROR [r1, r2: Rect]= CODE; RectCreate: PUBLIC PROC [xMin, yMin, xMax, yMax: INT] RETURNS[Rect]= { IF xMin > xMax OR yMin> yMax THEN {RETURN[NIL]}; RETURN [NEW[RectRep _ [x: IntlCreate[xMin, xMax], y: IntlCreate[yMin, yMax]]]] }; --RectCreate -- RectCopy: PUBLIC PROC[r: Rect] RETURNS [Rect] ={ IF r = NIL THEN RETURN [NIL]; RETURN [NEW[RectRep _[x: IntlCopy[r.x], y: IntlCopy[r.y]] ]] }; --RectCopy-- RectOneOf: PUBLIC PROC[r: Rect] RETURNS[MiscOneOf] ={ IF r = NIL THEN RETURN [empty]; SELECT IntlOneOf[r.x] FROM interval => {SELECT IntlOneOf[r.y] FROM interval => RETURN[rect]; point => RETURN[interval]; ENDCASE => ERROR}; point => {SELECT IntlOneOf[r.y] FROM interval => RETURN[interval]; point => RETURN[point]; ENDCASE => ERROR}; ENDCASE => ERROR}; --RectOneOf-- RectIntersect: PUBLIC PROC [r1, r2: Rect] RETURNS[Rect]= { xI, yI: Interval; IF r1 = NIL OR r2 = NIL THEN RETURN[NIL]; xI _ IntlIntersect[r1.x, r2.x]; yI _ IntlIntersect[r1.y, r2.y]; IF xI = NIL OR yI = NIL THEN RETURN[NIL]; RETURN[NEW[RectRep _ [x: xI, y: yI]]]; }; -- RectIntersect-- RectContainp: PUBLIC PROC [r1, r2: Rect] RETURNS[BOOL]= { IF r2 =NIL THEN RETURN [TRUE]; IF r1 = NIL THEN RETURN [r2 = NIL]; RETURN[IntlContainp[r1.x, r2.x] AND IntlContainp[r1.y, r2.y]]; }; -- RectContainp-- RectContainPt: PUBLIC PROC[r: Rect, xCoord, yCoord: INT] RETURNS [BOOL] ={ IF r = NIL THEN RETURN [FALSE]; RETURN [IntlContainPt[r.x, xCoord] AND IntlContainPt[r.y, yCoord]]};--RectContainPt-- RectArea: PUBLIC PROC[r: Rect] RETURNS[NAT] ={ IF r = NIL THEN RETURN [0]; RETURN [IntlLength[r.x] * IntlLength[r.y]]}; --RectArea-- RectMakeBRect: PUBLIC PROC [r1, r2: Rect] RETURNS[Rect]= { IF r1 = NIL THEN RETURN [RectCopy[r2]]; IF r2 = NIL THEN RETURN [RectCopy[r1]]; RETURN [NEW[RectRep _ [x: IntlMakeBIntl[r1.x, r2.x], y: IntlMakeBIntl[r1.y, r2.y]]]]; }; -- RectMakeBBox-- RectSubtract: PUBLIC PROC [r1, r2: Rect] RETURNS[Rect]= { ri: Rect; IF r1 = NIL OR r2 = NIL THEN RETURN [RectCopy[r1]]; IF RectContainp[r2, r1] THEN RETURN[NIL]; IF r1.x.max < r2.x.min OR r2.x.max < r1.x.min OR r1.y.max < r2.y.min OR r2.y.max < r1.y.min THEN RETURN [RectCopy[r1]]; ri _ RectIntersect[r1, r2]; IF IntlContainp[ri.x, r1.x] THEN {RETURN [NEW[RectRep _[x: r1.x, y: IntlSubtract[r1.y, ri.y! IntlSubtractFailure => GOTO subtractFailed]]]]}; IF IntlContainp[ri.y, r1.y] THEN {RETURN [NEW[RectRep _[x: IntlSubtract[r1.x, ri.x ! IntlSubtractFailure =>GOTO subtractFailed], y: r1.y]]]}; GOTO subtractFailed; EXITS subtractFailed => RETURN WITH ERROR RectSubtractFailure[r1, r2]; }; -- RectSubtract-- RectPaint: PUBLIC PROC[r: Rect, context: Graphics.Context, xOffset, yOffset: REAL, scaleFactor: REAL _ 1.0, stipple: CARDINAL _ IPConstants.Gray, noFill: BOOL _ FALSE] ={ originX, originY: REAL; spanX, spanY: REAL; SELECT RectOneOf[r] FROM rect => {path: Graphics.Path _ Graphics.NewPath[]; originX _ xOffset + scaleFactor * r.x.min; originY _ yOffset + scaleFactor * r.y.min; spanX _ xOffset + scaleFactor * r.x.max; spanY _ yOffset + scaleFactor * r.y.max; Graphics.MoveTo[path, originX, originY, FALSE]; Graphics.LineTo[path, spanX, originY]; Graphics.LineTo[path, spanX, spanY]; Graphics.LineTo[path, originX, spanY]; Graphics.LineTo[path, originX, originY]; IF noFill THEN {Graphics.DrawStroke[context, path]} ELSE {Graphics.SetStipple[context, stipple]; Graphics.DrawArea[context, path]}}; interval, point => {delta: INT _ 1; originX _ xOffset + scaleFactor * (r.x.min - delta); originY _ yOffset + scaleFactor * (r.y.min - delta); spanX _ xOffset + scaleFactor * (r.x.max + delta); spanY _ yOffset + scaleFactor * (r.y.max + delta); Graphics.SetStipple[context, IPConstants.Black]; Graphics.SetCP[context, originX, originY]; Graphics.DrawTo[context, spanX, originY]; Graphics.DrawTo[context, spanX, spanY]; Graphics.DrawTo[context, originX, spanY]; Graphics.DrawTo[context, originX, originY];}; empty => NULL; ENDCASE => ERROR; }; --RectPaint-- x: PUBLIC PROC [r: Rect] RETURNS [Misc.Interval] ={ RETURN [IF r = NIL THEN NIL ELSE r.x]}; --x-- y: PUBLIC PROC[r: Rect] RETURNS [Misc.Interval] = { RETURN [IF r = NIL THEN NIL ELSE r.y]}; --y-- xMin: PUBLIC PROC [r: Rect] RETURNS[INT]= {RETURN[r.x.min]}; --xMin -- yMin: PUBLIC PROC [r: Rect] RETURNS[INT]= {RETURN [r.y.min]}; -- yMin-- xMax: PUBLIC PROC [r: Rect] RETURNS[INT]= {RETURN [r.x.max]}; -- xMax-- yMax: PUBLIC PROC [r: Rect] RETURNS[INT]= {RETURN [r.y.max]}; --yMax -- IntlSubtractFailure: PUBLIC ERROR [i1, i2: Interval]= CODE; IntlCreate: PUBLIC PROC [min, max: INT] RETURNS[Interval]= { IF min> max THEN {RETURN[NIL]}; RETURN[NEW[IntervalRep _ [min, max]]]; }; -- IntlCreate-- IntlCopy: PUBLIC PROC[i: Interval] RETURNS[Interval] ={ IF i = NIL THEN RETURN [NIL]; RETURN [NEW[IntervalRep _ [i.min, i.max]]]}; --IntlCopy-- IntlOneOf: PUBLIC PROC[i: Interval] RETURNS[MiscOneOf] ={ IF i = NIL THEN RETURN [empty]; SELECT i.min FROM < i.max => RETURN[interval]; i.max => RETURN[point]; ENDCASE => ERROR;}; --IntlOneOf-- IntlMakeBIntl: PUBLIC PROC[i1, i2: Interval] RETURNS[Interval] ={ IF i1 = NIL THEN RETURN [IntlCopy[i2]]; IF i2 = NIL THEN RETURN [IntlCopy[i1]]; RETURN [NEW[IntervalRep _ [MIN[i1.min, i2.min], MAX[i1.max, i2.max]]]] }; --IntlMakeBIntl-- IntlContainp: PUBLIC PROC [i1, i2: Interval] RETURNS[BOOL]= { IF i2 = NIL THEN RETURN [TRUE]; IF i1 = NIL THEN RETURN [i2 = NIL]; IF i1.min <= i2.min AND i2.max <= i1.max THEN {RETURN[TRUE]} ELSE {RETURN[FALSE]}}; -- IntlRectContainp-- IntlContainPt: PUBLIC PROC[i: Interval, p: INT] RETURNS[BOOL]= { IF i = NIL THEN RETURN [FALSE]; RETURN [i.min <= p AND p<= i.max ]};--IntlContainPt-- IntlLength: PUBLIC PROC[i: Interval] RETURNS[NAT] ={ IF i = NIL THEN RETURN [0]; RETURN [i.max - i.min]}; --intlLength-- IntlIntersect: PUBLIC PROC [i1, i2: Interval] RETURNS[Interval]= { IF i1 = NIL OR i2 = NIL THEN RETURN [NIL]; RETURN[IntlCreate[MAX[i1.min, i2.min], MIN[i1.max, i2.max]]]}; -- IntlIntersect-- IntlSubtract: PUBLIC PROC [i1, i2: Interval] RETURNS[Interval]= { IF i1 = NIL OR i2= NIL THEN RETURN [IntlCopy[i1]]; IF IntlContainp[i2, i1] THEN RETURN[NIL]; IF i1.max < i2.min OR i2.max < i1.min THEN RETURN [IntlCopy[i1]]; IF i1.min < i2.min AND i2.max < i1.max THEN {RETURN WITH ERROR IntlSubtractFailure[i1, i2]}; IF i1.min <= i2.max AND i2.max < i1.max THEN RETURN [NEW[IntervalRep _ [i2.max + 1, i1.max]]]; IF i1.min < i2.min AND i2.min <= i1.max THEN RETURN[NEW[IntervalRep _ [i1.min, i2.min - 1]]]; ERROR; }; --IntlSubtract -- --Raise IntlSubtractFailure- min: PUBLIC PROC [i: Interval] RETURNS [INT]= {RETURN[i.min]}; --min -- max: PUBLIC PROC [i: Interval] RETURNS [INT]= {RETURN[i.max]}; --max -- END. d-- File: MiscImpl.mesa -- Last Edited by: CSChow, February 1, 1985 0:42:38 am PST --Documentation will come later after consolidating the design -- -- curtain is unioned (in Set theory's sense) with previous curtains --Window is covered iff union of all Intervals contain it --TRUE <=> interval is contained in window and doesnt intersects any curtains -- TRUE <=> In the union of all previous curtains, 1 of them contains the interval --ChangeLog: -- January 2, 1985 10:28:57 pm PST -- (1) Add "IF r = NIL THEN RETURN [FALSE]; " to RectContainPt -- (2) Add IF r = NIL THEN NIL ELSE r. to x and y Κ κ˜Jšœ™Jšœ:™:J™J™AJ˜šΟk ˜ Jšœ œZ˜hJ˜ J˜J˜—šœ œ˜Jšœ ˜Jšœœœ˜J˜š Οn œœœ œœ ˜:Icodešœœ2œΟc˜T—šžœœœ ˜;K™DKšœœœ ˜-Kšœ œœœ˜Kšœœœœ˜.š œœœœœ˜=Kš œ#œœ!œ!œ-œ˜¦šœœ˜#Kšœœ œ%œ˜P—šœœ˜#Kšœœœ˜,—š˜Kšœœ ˜/—Kšœ˜—K˜KšœŸ˜—š ž œœœ œœ˜6K™9Kš œœœœ œ˜/š œœœœœ˜=Kšœ#œœœ ˜TKšœ˜—Kšœœ˜KšœŸ˜—š žœœœœœ˜GK™MKš œœœœœ˜6š œœœœœ˜=Kš œ!œœœœ˜:Kšœ˜—KšœœŸ˜"—š žœœœœœ˜OK™Rš œœœœœ˜=Kšœ!œœœ˜PKšœ˜—Kšœœ˜KšœŸ˜—K˜K˜—™Jšœœœœ˜7š ž œœœœœ ˜FJš œ œ œœœ˜0K•StartOfExpansion[]šœœC˜NJšœŸ˜—šžœœœ œ ˜0Kš œœœœœ˜Kšœœ1˜KšœŸ˜—š ž œœœœœœ˜JKš œœœœœ˜ KšœœŸ˜U—š žœœœ œœ˜.K–[]šœœœœ˜Kšœ'Ÿ ˜9—šž œœœœ ˜:Kšœœœœ˜'Kšœœœœ˜'KšœœJ˜UKšœŸ˜—šž œœœœ ˜9J˜ Jš œœœœœœ˜4Kšœœœœ˜*Kš œœœœœœ˜xK˜Kš œœœœGœ˜Kš œœœœ>œ˜Kšœ˜š˜Kšœœœœ˜A—JšœŸ˜—J™šž œœœ7œœœœœ˜ͺJšœœ˜Jšœœ˜šœ˜šœ2˜2Jšœ*˜*Jšœ*˜*Kšœ)˜)Kšœ(˜(Kšœ(œ˜/Kšœ&˜&Kšœ$˜$Kšœ&˜&Kšœ(˜(šœ˜ Kšœ&˜*KšœL˜P——šœœ˜#Kšœ4˜4Kšœ4˜4Kšœ3˜3Kšœ2˜2Kšœ0˜0Kšœ*˜*Kšœ)˜)Kšœ'˜'Kšœ)˜)Kšœ-˜-—Kšœ œ˜Jšœœ˜—JšœŸ ˜—šœœœ œ˜3Kš œœœœœœŸ˜-—šœœœ œ˜3KšœœœœœœŸœ˜.—Jš œœœ œœœ Ÿ ˜FKš œœœ œœœ Ÿ ˜GKš œœœ œœœ Ÿ ˜GKš œœœ œœœ Ÿ œ˜HJ˜Jšœœœœ˜;š ž œœœ œœ ˜Kš œ œœœœœ™6————…—!‚0Π