DIRECTORY CD USING [Design, Number, ObPtr, Rect], Rope USING [ROPE]; PWStretch: CEDAR DEFINITIONS = BEGIN ROPE: TYPE = Rope.ROPE; PosRange: TYPE = RECORD [min, max: CD.Number]; Segment: TYPE = REF SegmentRec; SegmentRec: TYPE = RECORD [ pos: PosRange, info: REF ANY _ NIL -- All other information ]; SortedSegments: TYPE = LIST OF Segment _ NIL; worldSegment: READONLY Segment; worldSortedSegments: READONLY SortedSegments; StretchInfo: TYPE = REF StretchInfoRec; StretchInfoRec: TYPE = RECORD [ value: CD.Number _ 0 -- Wanted value of stretch ]; StretchSegment: TYPE = Segment; SortedStretchSegments: TYPE = SortedSegments; PosRangeXFromRect: PROC [rect: CD.Rect] RETURNS [posrange: PosRange]; PosRangeYFromRect: PROC [rect: CD.Rect] RETURNS [posrange: PosRange]; RectFromPosRangeX: PROC [pos: PosRange, y: CD.Number] RETURNS [rect: CD.Rect]; RectFromPosRangeY: PROC [pos: PosRange, x: CD.Number] RETURNS [rect: CD.Rect]; IntersectPos: PROC [pos1, pos2: PosRange] RETURNS [intersect: BOOL]; OffsetPosRange: PROC [pos: PosRange, offset: INT] RETURNS [posrange: PosRange]; IntersectPosRange: PROC [pos1, pos2: PosRange] RETURNS [posrange: PosRange]; UnionPosRange: PROC [pos1, pos2: PosRange] RETURNS [posrange: PosRange]; MakeNewSegment: PROC [pos: PosRange, info: REF _ NIL] RETURNS [seg: Segment]; IntersectSeg: PROC [s1, s2: Segment] RETURNS [intersect: BOOL]; IntersectSegment: PROC [s1, s2: Segment, info: REF _ NIL] RETURNS [seg: Segment]; UnionSegment: PROC [s1, s2: Segment, info: REF _ NIL] RETURNS [seg: Segment]; CopySegment: PROC [s: Segment, offset: INT _ 0] RETURNS [seg: Segment]; IntersectPosSegs: PROC [pos: PosRange, segments: SortedSegments] RETURNS [inter: SortedSegments]; Append: PROC [s1: SortedSegments, s2: SortedSegments _ NIL, offset: INT _ 0] RETURNS [SortedSegments]; Reverse: PROC [list: SortedSegments] RETURNS [new: SortedSegments]; Intersect: PROC [list1, list2: SortedSegments] RETURNS [list: SortedSegments]; Union: PUBLIC PROC [list1, list2: SortedSegments] RETURNS [list: SortedSegments]; Insert: PROC [pos: PosRange, info: REF, list: SortedSegments _ NIL] RETURNS [SortedSegments]; Complement: PROC [list: SortedSegments, range: PosRange] RETURNS [SortedSegments]; GetStretchValue: PROC [s: StretchSegment] RETURNS [CD.Number]; InsertStretchSegment: PROC [pos: PosRange, value: CD.Number, s: SortedStretchSegments] RETURNS [SortedStretchSegments]; ComposeRectStretches: PROC [rect: CD.Rect, hor, ver: SortedStretchSegments] RETURNS [CD.Rect]; ParseStretchProc: TYPE = PROC [design: CD.Design, obj: CD.ObPtr] RETURNS [hor, ver: SortedSegments]; DoStretchProc: TYPE = PROC [design: CD.Design, obj: CD.ObPtr, hor, ver: SortedSegments] RETURNS [newObj: CD.ObPtr, errMsg: ROPE _ NIL]; ParseStretch: ParseStretchProc; DoStretch: DoStretchProc; HardObjParseStretch: ParseStretchProc; END. ªPWStretch.mesa Copyright c 1984 by Xerox Corporation. All rights reversed. Created by: Monier, November 19, 1984 10:01:05 am PST Last Edited by: Serlet, February 26, 1985 2:56:40 pm PST This interface defines in what frame works stretching, as used by PW. The idea is to do automatic stretching of uninteresting and non-critical cells as routing cells. To achieve this aim one must be able to parse any object, that is tell where it is possible to stretch, and to create a new object from given stretch constraints. We use a data structure called SortedSegments for different purposes. -- Data structures -- Easi! -- PosRange describe the projection of some rectangles on an edge. Attention, contrary to what Christian does to rectangles, min is included and max excluded. It is an unchecked error to create a PosRange with min>=max. -- Segment is PosRange plus additionnal information -- Sorted (in increasing pos order) list of Segments. Two Segments in a SortedSegments cannot intersect. The biggest segment possible, used as neutral element in some operations The biggest SortedSegments possible, used as neutral element in some operations Some Segments record stretch information, that is the wanted amount of stretch. This amount is stored in the info field of Segments. For documenting purposes, we define new types for segments which have a StretchInfo in their info field. -- Operations on those data structures -- Operations on PosRange -- Predicate telling if 2 PosRanges Intersects -- Offsets a PosRange by an INT amount -- Intersects 2 PosRange -- Union of 2 PosRange -- Operations on Segment -- Creates a new Segment -- Tells whether 2 segments do intersect -- Creates a new Segment at the intersection of 2 -- Creates a new Segment at the reunion of 2 -- Copies a segment with displacing it -- Operations on SortedSegments -- Returns the sorted list of all segments which intersect some given PosRange -- Appends a SortedSegments to an existing one, with copying and displacing the Segments. With only first argument, returns a top-level copy of it. -- Reverse a SortedSegments, as Lisp's reverse! In fact list is not really a SortedSegments before the call to reverse. -- Makes a new SortedSegments with all segments that appear in both lists -- Makes a new SortedSegments with all segments that appear in either lists -- Inserts a new Segment -- Makes a list with all segments in range that are excluded by list -- Operations on StretchSegment Inserts a new StretchSegment at pos with value value, unless there is already one, in case it only add the stretch value to the present one. -- Computes the new location of a Rect once composed with the given SortedStretchSegments -- Stretch related operations Every class of object must register a $ParseStretchProc with CDObjectProcs. Default is NOT stretchable. It is also possible to put a ParseStretchProc on a particular object, under the property name $ParseStretchProc. Every stretchable object must register a $DoStretchProc with CDObjectProcs. It is also possible to put a DoStretchProc on a particular instance of object, under the attribute $DoStretchProc. -- design is the design into the new object should be entered. It is the same design in which the object comes from. -- obj is the object to be stretched -- hor and ver are a list of segments telling where we want to do the stretch. The info field of segments contains an integer which is the amount of stretch desired. -- newObj is a new obj or NIL if something went wrong (in that case errMsg is a rope telling what went wrong). -- Given any cell, tells where the stretch areas are -- Given cell and wanted stretches, return a new cell -- Used for telling that an object is not stretchable Êr˜šœ™Jšœ Ïmœ1™J˜JšœŒ™ŒJš¡œžœžœ#žœ˜wJ˜JšœY™YJš Ðbnœžœžœ(žœžœ˜^——J˜™J™JšœWÐbkœ~™ØJš ¡œžœžœ žœžœžœ˜dJ˜JšœÀ™ÀJ™uJšœ$™$Jšœ¥™¥Jšœn™nJš¢ œžœžœ žœžœ"žœ žœžœžœ˜‡J™J™4JšŸ œ˜J˜J™5JšŸ œ˜J™J™5JšŸœ˜&—J˜Jšžœ˜—J˜J˜J˜—…— :V