GGModelTypes.mesa
Copyright Ó 1987, 1988 by Xerox Corporation. All rights reserved.
Stone, August 5, 1985 2:13:37 pm PDT
Pier, July 18, 1991 7:41 pm PDT
Bier, December 2, 1991 11:13 am PST
Eisenman, October 2, 1987 6:51:08 pm PDT
Kurlander - August 20, 1987 11:33:32 pm PDT
DIRECTORY
FeedbackTypes, GGBasicTypes, GGCoreTypes, GGHistoryTypes, GGSegmentTypes, Imager, ImagerFont, ImagerPath, ImagerTransformation, IO, Prop, Rope, Rosary;
GGModelTypes: CEDAR DEFINITIONS = BEGIN
BitMatrix: TYPE = GGBasicTypes.BitMatrix;
BitVector: TYPE = GGBasicTypes.BitVector;
BoundBox: TYPE = GGCoreTypes.BoundBox;
Circle: TYPE = GGBasicTypes.Circle;
MsgRouter: TYPE = FeedbackTypes.MsgRouter;
HistoryEvent: TYPE = GGHistoryTypes.HistoryEvent;
Joint: TYPE = GGSegmentTypes.Joint;
Line: TYPE = GGCoreTypes.Line;
Point: TYPE = GGBasicTypes.Point;
Scene: TYPE = REF SceneObj;
SceneObj: TYPE; -- Opaque Type, Implemented by GGSceneImpl
Segment: TYPE = GGSegmentTypes.Segment;
SelectedObjectData: TYPE = GGSegmentTypes.SelectedObjectData;
SelectionClass: TYPE = GGSegmentTypes.SelectionClass;
SequenceOfReal: TYPE = GGCoreTypes.SequenceOfReal;
StrokeEnd: TYPE = Imager.StrokeEnd; -- TYPE = {square, butt, round}
StrokeJoint: TYPE = Imager.StrokeJoint; -- TYPE = {miter, bevel, round}
Transformation: TYPE = ImagerTransformation.Transformation;
Vector: TYPE = GGBasicTypes.Vector;
MoveToProc: TYPE = ImagerPath.MoveToProc;
LineToProc: TYPE = ImagerPath.LineToProc;
CurveToProc: TYPE = ImagerPath.CurveToProc;
ConicToProc: TYPE = ImagerPath.ConicToProc;
ArcToProc: TYPE = ImagerPath.ArcToProc;
Constraints
EditConstraints: TYPE = {none, tangent, length}; -- For now to avoid Dependency
BezierDragRecord: TYPE = RECORD [ -- For now while not a general constraint implementation
draggingBezier: BOOLFALSE,
trajEnd: TrajEnd ← lo,
bezierNum: NAT ← 0,
traj: Traj ← NIL,
outlineSlice: Slice ← NIL
];
Joint and Control Point sizes
jointSize: REAL = 6;
halfJointSize: REAL = 3;
hotJointSize: REAL = 10;
halfHotJointSize: REAL = 5;
Camera
Camera: TYPE = REF CameraObj;
CameraObj: TYPE = RECORD [
quality: QualityMode ← fast,
displayStyle: DisplayStyle ← print,
hideHot: BOOLFALSE,
hideAlignments: BOOLFALSE,
cpScale: REAL ← 1.0 -- scale control points about their centers by this factor before drawing
];
DisplayStyle: TYPE = {print, screen};
print uses Press fonts on the screen.
screen uses Tioga fonts on the screen
QualityMode: TYPE = {fast, showall, quality};
fast is for interactive use.
showall is for making interpress masters which look like the screen.
quality is for previewing masters on the screen and making interpress masters for final artwork.
Default
FontData: TYPE = REF FontDataRec;
FontDataRec: TYPE = RECORD [
literal: Rope.ROPE, -- "xerox/xc1-2-2/Modern-bold-italic"
prefix: Rope.ROPE,-- "xerox/xc1-2-2/"
literalFSF: Rope.ROPE, -- literal familySizeFace: "Modern-bold-italic"
userFSF: Rope.ROPE, -- user familySizeFace: "Modern-BI"
family: Rope.ROPE, -- family: "Modern"
transform: ImagerTransformation.Transformation,
scale: REAL ← 1.0,
storedSize: REAL ← 1.0,
designSize: REAL ← 1.0,
comfortable: BOOLFALSE,
bold, italic, faceKnown: BOOLFALSE,
substituteOK: BOOLFALSE,
substituted: BOOLFALSE,
namelessFont: ImagerFont.Font ← NIL
];
DefaultData: TYPE = REF DefaultDataObj;
DefaultDataObj: TYPE = RECORD [
strokeWidth: REAL ← 2.0,
strokeJoint: StrokeJoint ← round,
strokeEnd: StrokeEnd ← round,
dashed: BOOLFALSE,
pattern: SequenceOfReal,
offset: REAL ← 0.0,
length: REAL ← 0.0,
strokeColor: Imager.Color,-- no color
fillColor: Imager.Color ← NIL, -- no fill
font: FontData,
textColor: Imager.Color ← NIL,
dropShadowOn: BOOLFALSE,
dropShadowOffset: Vector ← [-0.1, -0.1],
dropShadowColor: Imager.Color ← NIL
];
Slices
SliceParts: TYPE = REF ANY;
This is a distinguished value to be used to mean "all of the parts of the accompanying Gargoyle slice". It is a companion to NIL which means "none of the parts".
SliceDescriptor: TYPE = REF SliceDescriptorObj;
SliceDescriptorObj: TYPE = RECORD [
slice: Slice,
parts: SliceParts
];
Slice: TYPE = REF SliceObj;
SliceObj: TYPE = RECORD [
class: SliceClass,
data: REF ANY,
parent: Slice, -- for when slices can be part of clusters
selectedInFull: SelectedObjectData,
normalSelectedParts: SliceDescriptor, -- maintained by GGSelect to improve performance
hotSelectedParts: SliceDescriptor, -- maintained by GGSelect to improve performance
activeSelectedParts: SliceDescriptor, -- maintained by GGSelect to improve performance
matchSelectedParts: SliceDescriptor, -- maintained by GGSelect to improve performance
nullDescriptor: SliceDescriptor, -- to reduce allocations when there is nothing to report
fullDescriptor: SliceDescriptor, -- to reduce allocations when everything is selected
tightBox: BoundBox ← NIL,
tightBoxValid: BOOLFALSE, -- added Bier, March 12, 1988
boundBox: BoundBox ← NIL,
boxValid: BOOLFALSE,
onOverlay: BOOLFALSE,
extraPoints: LIST OF Joint,
priority: INT ← 0, -- scene order priority. 0 => in back
historyTop: INT ← 0, -- index of latest history event touching this slice
cacheHint: CARD32LAST[CARD32],-- where to look in the image cache for this slice's class to find a previously rendered version of this shape
props: Prop.PropList
];
SliceClass: TYPE = REF SliceClassObj;
SliceClassObj: TYPE = RECORD [
type: ATOM,
Fundamentals
getBoundBox: SliceBoundBoxProc, -- includes space for stroke width and control points
getTransformedBoundBox: SliceTransformedBoundBoxProc, -- includes space for stroke width and control points
getTightBox: SliceTightBoxProc, -- fits tightly around the graphical part of the slice
copy: SliceCopyProc,
unlink: SliceUnlinkProc,
restore: SliceRestoreProc,
Drawing
buildPath: SliceBuildPathProc,
drawBorder: SliceDrawBorderProc,
drawParts: SliceDrawPartsProc,
drawTransform: SliceDrawTransformProc,
drawSelectionFeedback: SliceDrawSelectionFeedbackProc,
drawAttractorFeedback: SliceDrawAttractorFeedbackProc,
attractorFeedbackBoundBox: SliceAttractorFeedbackBoundBoxProc ← NIL,
saveSelections: SliceSaveSelectionsProc,
remakeSelections: SliceRemakeSelectionsProc,
Transforming
transform: SliceTransformProc,
Textual Description
describe: SliceDescribeProc,
describeHit: SliceDescribeHitProc,
fileout: SliceFileoutProc,
filein: SliceFileinProc,
Parts
isEmptyParts: SliceIsEmptyPartsProc,
isCompleteParts: SliceIsCompletePartsProc,
newParts: SliceNewPartsProc,
unionParts: SliceUnionPartsProc,
differenceParts: SliceDifferencePartsProc,
movingParts: SliceMovingPartsProc,
augmentParts: SliceAugmentPartsProc,
alterParts: SliceAlterPartsProc,
setSelectedFields: SliceSetSelectedFieldsProc,
Part Generators
pointsInDescriptor: SlicePointsInDescriptorProc,
walkPointsInDescriptor: SliceWalkPointsInDescriptorProc,
pointPairsInDescriptor: SlicePointPairsInDescriptorProc,
segmentsInDescriptor: SliceSegmentsInDescriptorProc,
walkSegments: SliceWalkSegmentsProc,
nextPoint: SliceNextPointProc,
nextPointPair: SliceNextPointPairProc,
nextSegment: SliceNextSegmentProc,
Hit Testing
closestPoint: SliceClosestPointProc,
closestJointToHitData: SliceClosestJointToHitDataProc,
closestPointAndTangent: SliceClosestPointAndTangentProc,
closestSegment: SliceClosestSegmentProc,
filledPathsUnderPoint: SliceFilledPathsUnderPointProc,
lineIntersection: SliceLineIntersectionProc,
circleIntersection: SliceCircleIntersectionProc,
hitDataAsSimpleCurve: SliceHitDataAsSimpleCurveProc,
Style
setDefaults: SliceSetDefaultsProc,
setStrokeWidth: SliceSetStrokeWidthProc,
getStrokeWidth: SliceGetStrokeWidthProc,
setStrokeEnd: SliceSetStrokeEndProc,
getStrokeEnd: SliceGetStrokeEndProc,
setStrokeJoint: SliceSetStrokeJointProc,
getStrokeJoint: SliceGetStrokeJointProc,
setStrokeColor: SliceSetStrokeColorProc,
getStrokeColor: SliceGetStrokeColorProc,
setFillColor: SliceSetFillColorProc,
getFillColor: SliceGetFillColorProc,
setArrows: SliceSetArrowsProc,
getArrows: SliceGetArrowsProc,
setDashed: SliceSetDashedProc,
getDashed: SliceGetDashedProc,
setOrientation: SliceSetOrientationProc,
getOrientation: SliceGetOrientationProc
];
SlicePartsWalkProc: TYPE = PROC [Slice, SliceParts] RETURNS [done: BOOLFALSE];
SliceDescriptorWalkProc: TYPE = PROC [SliceDescriptor] RETURNS [done: BOOLFALSE];
SliceDescriptorTallyProc: TYPE = PROC [sliceD: SliceDescriptor] RETURNS [visitChildren: BOOL, keepD: SliceDescriptor, done: BOOLFALSE];
SliceTallyProc: TYPE = PROC [slice: Slice] RETURNS [visitChildren: BOOL, keep: BOOL, done: BOOLFALSE];
SliceWalkProc: TYPE = PROC [Slice] RETURNS [done: BOOLFALSE];
WalkLevel: TYPE = {first, leaf, all, highest};
Fundamental Slice Routines (NIL Parts => All)
SliceBoundBoxProc: TYPE = PROC [slice: Slice, parts: SliceParts ← NIL] RETURNS [box: BoundBox];
Returns the geometric bound box for the named parts of the slice. IF parts = NIL, find the boundBox of the whole slice. The returned boundbox will allow space for control points and stroke width.
SliceTransformedBoundBoxProc: TYPE = PROC [slice: Slice, selectedParts: SliceParts, movingParts: SliceParts, transform: Transformation ← NIL] RETURNS [box: BoundBox];
Returns the geometric bound box for the named parts of the slice. IF parts = NIL, find the bound box of the whole slice. The returned bound box will allow space for control points and stroke width. If transform#NIL, the named parts of the slice are first transformed before the bound box is calculated.
SliceTightBoxProc: TYPE = PROC [slice: Slice, parts: SliceParts ← NIL] RETURNS [box: BoundBox];
Returns the tight fitting geometric bound box for the named parts of the slice. IF parts = NIL, find the boundBox of the whole slice.
SliceCopyProc: TYPE = PROC [slice: Slice, parts: SliceParts ← NIL] RETURNS [copy: LIST OF Slice];
Returns a set of new slices for the parts of the slice. IF parts = NIL, copy the entire slice and return a single element list.
SliceUnlinkProc: TYPE = PROC [slice: Slice];
Does class-specific processing to eliminate circular data structures and other REFS. SliceUnlinkProc is only called when the Slice is about to disappear forever, to allow the Cedar gargbage collector to sweep up. Proc may be called more than once for the same slice.
SliceRestoreProc: TYPE = PROC [from: Slice, to: Slice];
Moves the contents of the "from" slice into the "to" slice by following REF chains as needed. The "from" and "to" objects must be identically or similarly structured. Used by the undo mechanism to restore a particular piece of storage to an earlier state.
Drawing (Parts = NIL means All except as noted.)
SliceBuildPathProc: TYPE = PROC [slice: Slice, transformParts: SliceParts, transform: Transformation, moveTo: MoveToProc, lineTo: LineToProc, curveTo: CurveToProc, conicTo: ConicToProc, arcTo: ArcToProc, editConstraints: EditConstraints ← none];
SliceBuildPathProc may be called by clients needing the slice contribution to a path. It is designed for use in drawing objects via Imager.MaskFill or Imager.MaskStroke. transformParts=NIL => complete parts. transform=NIL => don't transform any parts. Otherwise, transform those pieces of the slice indicated in transformParts by the tranformation in transform, then use the five callback procs to create the slice path.
SliceDrawBorderProc: TYPE = PROC [slice: Slice, drawParts: SliceParts, transformParts: SliceParts, transform: Transformation, dc: Imager.Context, camera: Camera, quick: BOOLFALSE, editConstraints: EditConstraints ← none];
SliceDrawBorderProc may be called by clients needing the slice to actually draw a part of its border. drawParts=NIL => draw ALL parts. transformParts=NIL => transform ALL parts. transform=NIL => don't transform any parts. Otherwise, transform those pieces of the slice indicated in transformParts by the tranformation in transform, then draw those parts indicated in drawParts. SliceDrawBorderProc will do no fill operations, and may or may not use the corresponding SliceBuildPathProc for stroking.
SliceDrawPartsProc: TYPE = PROC [slice: Slice, parts: SliceParts ← NIL, dc: Imager.Context, camera: Camera, quick: BOOL];
Slice draws its parts into the Imager context. IF parts = NIL, draw the whole slice.
SliceDrawTransformProc: TYPE = PROC [slice: Slice, parts: SliceParts, dc: Imager.Context, camera: Camera, transform: Transformation, editConstraints: EditConstraints];
Slice applies transformation (temporarily) to its indicated parts, then draws itself into the Imager context. Used for rubberbanding or dragging. If parts = NIL transform the whole slice????
SliceDrawSelectionFeedbackProc: TYPE = PROC [slice: Slice, selectedParts: SliceParts, hotParts: SliceParts, dc: Imager.Context, camera: Camera, dragInProgress, caretIsMoving, hideHot, quick: BOOL];
Slice draws its selection feedback, as indicated by its parts, into the Imager context. quick is a flag which, if set, causes the slice to draw an abbreviated version of its selection feedback. During motion is true if anything in the scene is currently moving. Hide hot is TRUE if hotness feedback should not be shown. Draw nothing if the parts are NIL.
SliceDrawAttractorFeedbackProc: TYPE = PROC [slice: Slice, attractorParts: SliceParts, selectedParts: SliceParts, dragInProgress: BOOL, dc: Imager.Context, camera: Camera, editConstraints: EditConstraints];
sliceD is a simple SliceDescriptor describing where on the slice, the caret has been placed. The slice should draw appropriate feedback. attractorParts should not be NIL if anything is to be drawn.
SliceAttractorFeedbackBoundBoxProc: TYPE = PROC [slice: Slice, attractorParts: SliceParts, selectedParts: SliceParts, dragInProgress: BOOL, camera: Camera, editConstraints: EditConstraints] RETURNS [box: BoundBox];
sliceD is a simple SliceDescriptor describing where on the slice, the caret has been placed. Return the bounding box of the attractor feedback that will be drawn when the SliceDrawAttractorFeedbackProc is called with these same arguments.
SliceSaveSelectionsProc: TYPE = PROC [slice: Slice, parts: SliceParts, selectClass: SelectionClass];
If parts=NIL, use the selectClass to find the selected slice and save all of its selections. If parts#NIL, ignore scene and treat parts as the selection parts to be saved.
SliceRemakeSelectionsProc: TYPE = PROC [slice: Slice, selectClass: SelectionClass] RETURNS [parts: SliceParts];
Rebuild selected parts from the saved selections within the slice. IF slice is top level, then select exactly those parts for the given select class within the given scene, and return NIL. IF slice is not top level, return remade selected parts to caller.
Transforming
SliceTransformProc: TYPE = PROC [slice: Slice, parts: SliceParts ← NIL, transform: Transformation, editConstraints: EditConstraints, history: HistoryEvent];
Apply the given transformation to internal data of the slice as specified by parts. It is now in a new position, orientation, scaling, or skewing. When parts = NIL?
Textual Description (NIL means nothing)
SliceDescribeProc: TYPE = PROC [sliceD: SliceDescriptor] RETURNS [rope: Rope.ROPE];
Return a short description of slice and parts suitable for feedback line.
SliceDescribeHitProc: TYPE = PROC [slice: Slice, hitData: REF ANY] RETURNS [rope: Rope.ROPE];
Return a short description of hitData suitable for feedback line.
SliceFileoutProc: TYPE = PROC [slice: Slice, f: IO.STREAM];
Write a description of yourself onto stream f.
SliceFileinProc: TYPE = PROC [f: IO.STREAM, version: REAL, router: MsgRouter, camera: Camera] RETURNS [slice: Slice];
Read a description of yourself from stream f. The camera is passed as an argument because some slices (e.g., $Text) change shape depending on the current viewing parameters.
Parts (Parts = NIL means empty)
ExtendMode: TYPE = {literal, joint, controlPoint, segment, segmentRange, traj, slice, topLevel, none};
SelectMode: TYPE = ExtendMode;
SelectMode is used in SliceNewPartsProc. It is used to decide what kind of descriptor to build given a Slice and a HitData. It is interpreted as follows:
literal => Select the hit part.
joint => Select a joint or control point near the hit part.
controlPoint => Has no meaning for SliceNewPartsProc.
segment => Select a segment near that hit part.
segmentRange => Has no meaning for SliceNewPartsProc.
traj => Select the entire path that includes the hit part.
slice => Select the entire slice that most immediately includes the hit part.
topLevel => Select the largest slice that includes the slice that includes the hit part.
none => return an empty descriptor.
SliceIsEmptyPartsProc: TYPE = PROC [sliceD: SliceDescriptor] RETURNS [BOOL];
When sliceD.parts = NIL, this returns TRUE.
SliceIsCompletePartsProc: TYPE = PROC [sliceD: SliceDescriptor] RETURNS [BOOL];
When sliceD.parts = NIL, this returns FALSE.
SliceNewPartsProc: TYPE = PROC [slice: Slice, hitData: REF ANY, mode: SelectMode] RETURNS [sliceD: SliceDescriptor];
Returns a class-specific description of its parts to be used in calls to SelectSlice. Parts are determined from the mode and from the hitData within the slice, which was set by the slice during calls to SliceClosest* procs.
SliceUnionPartsProc: TYPE = PROC [partsA: SliceDescriptor, partsB: SliceDescriptor] RETURNS [aPlusB: SliceDescriptor];
Takes two parts descriptions and returns their union. This routine is used by the ExtendSelection routines.
SliceDifferencePartsProc: TYPE = PROC [partsA: SliceDescriptor, partsB: SliceDescriptor] RETURNS [aMinusB: SliceDescriptor];
Takes two parts descriptions and returns their difference. This routine is used by the Deselection routines.
SliceMovingPartsProc: TYPE = PROC [slice: Slice, selectedParts: SliceParts, editConstraints: EditConstraints, bezierDrag: BezierDragRecord] RETURNS [background, overlay, rubber, drag: SliceDescriptor];
We are about to perform a drag operation. Some parts of the object will stay in the background plane, some will be drawn on the overlay plane but stay stationary, some will rubber-band, and some will be dragged as a unit. This procedure identifies these four classes of parts.
SliceAugmentPartsProc: TYPE = PROC [sliceD: SliceDescriptor, selectClass: SelectionClass] RETURNS [more: SliceDescriptor];
Takes a parts description (usually the selected parts just before a SelectSlice operation) and returns a parts descriptor which describes parts which should be selected as well. Used so that slices with segment/joint analogies can behave like polygons.
SliceAlterPartsProc: TYPE = PROC [sliceD: SliceDescriptor, action: ATOM] RETURNS [alteredD: SliceDescriptor];
action may be $Forward, $Backward, $ShrinkForward, $Grow (as of November 9, 1988)
SliceSetSelectedFieldsProc: TYPE = PROC [sliceD: SliceDescriptor, selected: BOOL, selectClass: SelectionClass];
Part Generators (Parts = NIL means ?)
PointAndDone: TYPE = RECORD [point: Point, done: BOOL];
PointPairAndDone: TYPE = RECORD [lo, hi: Point, done: BOOL];
SlicePointsInDescriptorProc: TYPE = PROC [sliceD: SliceDescriptor] RETURNS [pointGen: PointGenerator];
PointWalkProc: TYPE = PROC [point: Point] RETURNS [done: BOOL FALSE];
SliceWalkPointsInDescriptorProc: TYPE = PROC [sliceD: SliceDescriptor, walkProc: PointWalkProc];
SlicePointPairsInDescriptorProc: TYPE = PROC [sliceD: SliceDescriptor] RETURNS [pointPairGen: PointPairGenerator];
SliceSegmentsInDescriptorProc: TYPE = PROC [sliceD: SliceDescriptor] RETURNS [segGen: SegmentGenerator];
SliceWalkSegmentsProc: TYPE = PROC [slice: Slice, walkProc: WalkProc] RETURNS [sliceD: SliceDescriptor];
The SliceWalkSegmentsProc takes a slice and calls the walkProc for each segment in the slice with the segment data and possibly an associated transformation. It returns a slice descriptor which describes all segments of the slice for which the walkProc returned TRUE.
WalkProc: TYPE = PROC [seg: Segment, transform: Transformation] RETURNS [keep: BOOL];
SliceNextPointProc: TYPE = PROC [slice: Slice, pointGen: PointGenerator] RETURNS [pointAndDone: PointAndDone];
SliceNextPointPairProc: TYPE = PROC [slice: Slice, pointPairGen: PointPairGenerator] RETURNS [pointPairAndDone: PointPairAndDone];
SliceNextSegmentProc: TYPE = PROC [slice: Slice, segGen: SegmentGenerator] RETURNS [seg: Segment, transform: Transformation];
Hit Testing (These descriptors don't have NIL parts)
SliceClosestPointProc: TYPE = PROC [sliceD: SliceDescriptor, testPoint: Point, tolerance: REAL] RETURNS [bestPoint: Point, bestDist: REAL, bestNormal: Vector, hitData: REF ANY, success: BOOL];
Used for hit testing. Find the nearest point on the parts of sliceD to testPoint. If the nearest point is farther away than tolerance units, this procedure may opt to return success = FALSE. If a valid point is returned, then success = TRUE. The proc should fill in slice.hitData, which is class-specific data describing the actual part of the slice that was closest. For some classes, this data will be a joint number, if the class objects have joints.
SliceClosestJointToHitDataProc: TYPE = PROC [sliceD: SliceDescriptor, mapPoint, testPoint: Point, hitData: REF ANY] RETURNS [jointD: SliceDescriptor, point: Point, normal: Vector];
This slice has been hit somewhere (perhaps on a segment). Find the closest joint to that segment point. Return its position and a descriptor of it.
SliceClosestPointAndTangentProc: TYPE = PROC [sliceD: SliceDescriptor, testPoint: Point, tolerance: REAL] RETURNS [bestPoint: Point, bestDist: REAL, tangent: Vector, hitData: REF ANY, success: BOOL];
Used for hit testing. Find the nearest point on the parts of sliceD to testPoint and the tangent vector (towards hi end of segment) at that point. If the nearest point is farther away than tolerance units, this procedure may opt to return success = FALSE. If a valid point is returned, then success = TRUE. The proc should fill in slice.hitData, which is class-specific data describing the actual part of the slice that was closest. For some classes, this data will be a joint number, if the class objects have joints.
SliceClosestSegmentProc: TYPE = PROC [sliceD: SliceDescriptor, testPoint: Point, tolerance: REAL] RETURNS [bestPoint: Point, bestDist: REAL, bestNormal: Vector, hitData: REF ANY, success: BOOL];
Used for hit testing. Find the nearest segment of the parts of sliceD to testPoint. If the nearest point is farther away than tolerance units, this procedure may opt to return success = FALSE. If the nearest point is farther away than tolerance units, this procedure may opt to return success = FALSE. If a valid point is returned, then success = TRUE. The proc should fill in slice.hitData, which is class-specific data describing the actual part of the slice that was closest. For some classes, this data will be a segment number, if the class objects has segments.
SliceFilledPathsUnderPointProc: TYPE = PROC [slice: Slice, point: Point, tolerance: REAL] RETURNS [hitData: REF ANYNIL, moreHitDatas: LIST OF REF ANYNIL];
Lists those paths (trajectories) of slice that have non-NIL fill color and whose interiors are directly behind the cursor. To make this routine easier to implement, we allow this routine to return both false positives and false negatives so long as they are made within distance "tolerance" of the boundary of a given path. This allows, for instance, curves to be approximated by polylines. If no paths of slice are behind point, returns [NIL, NIL]. If there are n such paths, moreHitDatas contains a list of numbers 2 through n.
SliceLineIntersectionProc: TYPE = PROC [sliceD: SliceDescriptor, line: Line] RETURNS [points: LIST OF Point, pointCount: NAT];
Finds the intersection of the line with those slice parts mentioned in sliceD.
SliceCircleIntersectionProc: TYPE = PROC [sliceD: SliceDescriptor, circle: Circle] RETURNS [points: LIST OF Point, pointCount: NAT];
Finds the intersection of the circle with those slice parts mentioned in sliceD.
SliceHitDataAsSimpleCurveProc: TYPE = PROC [slice: Slice, hitData: REF ANY] RETURNS [simpleCurve: REF ANY];
simpleCurve will be of type Edge, Arc, etc. There will be Conic and Bezier types as well.
Style (Parts = NIL means ?)
SliceSetDefaultsProc: TYPE = PROC [slice: Slice, parts: SliceParts, defaults: DefaultData, history: HistoryEvent];
SliceSetStrokeWidthProc: TYPE = PROC [slice: Slice, parts: SliceParts, strokeWidth: REAL, history: HistoryEvent] RETURNS [box: BoundBox];
Sets the stroke width of the named parts of slice to be strokeWidth. Returns the bounding box of all elements of the slice that will require refreshing as a result of the change.
SliceGetStrokeWidthProc: TYPE = PROC [slice: Slice, parts: SliceParts] RETURNS [strokeWidth: REAL ← 0.0, isUnique: BOOLTRUE];
Get the stroke width of the named parts of slice.
SliceSetStrokeEndProc: TYPE = PROC [slice: Slice, parts: SliceParts, strokeEnd: StrokeEnd, history: HistoryEvent];
Sets the stroke end of the named parts of slice to be strokeEnd.
SliceGetStrokeEndProc: TYPE = PROC [slice: Slice, parts: SliceParts] RETURNS [strokeEnd: StrokeEnd ← round, isUnique: BOOLTRUE];
Get the stroke end of the named parts of slice.
SliceSetStrokeJointProc: TYPE = PROC [slice: Slice, parts: SliceParts, strokeJoint: StrokeJoint, history: HistoryEvent];
Sets the stroke Joint of the named parts of slice to be strokeJoint.
SliceGetStrokeJointProc: TYPE = PROC [slice: Slice, parts: SliceParts] RETURNS [strokeJoint: StrokeJoint ← round, isUnique: BOOLTRUE];
Get the stroke Joint of the named parts of slice.
SliceSetStrokeColorProc: TYPE = PROC [slice: Slice, parts: SliceParts, color: Imager.Color, setHow: ATOM, history: HistoryEvent];
Sets the stroke color of the named parts of slice to be color.
SliceGetStrokeColorProc: TYPE = PROC [slice: Slice, parts: SliceParts] RETURNS [color: Imager.Color ← NIL, isUnique: BOOLTRUE];
Get the stroke color of the named parts of slice.
SliceSetFillColorProc: TYPE = PROC [slice: Slice, parts: SliceParts, color: Imager.Color, setHow: ATOM, history: HistoryEvent];
Sets the fill color of the slice to be color.
SliceGetFillColorProc: TYPE = PROC [slice: Slice, parts: SliceParts] RETURNS [color: Imager.Color ← NIL, isUnique: BOOLTRUE];
Get the fill color of the slice.
SliceSetArrowsProc: TYPE = PROC [slice: Slice, parts: SliceParts, leftDown, rightUp: BOOL, history: HistoryEvent];
Sets the arrow ends of the named parts of the slice.
SliceGetArrowsProc: TYPE = PROC [slice: Slice] RETURNS [leftDown, rightUp: BOOLFALSE];
Get the arrow ends of the named parts of the slice.
SliceSetDashedProc: TYPE = PROC [slice: Slice, parts: SliceParts, dashed: BOOL ← FALSE, pattern: SequenceOfReal ← NIL, offset: REAL ← 0.0, length: REAL ← -1.0, history: HistoryEvent];
SliceGetDashedProc: TYPE = PROC [slice: Slice, parts: SliceParts] RETURNS [dashed: BOOLFALSE, pattern: SequenceOfReal ← NIL, offset, length: REAL ← 0.0, isUnique: BOOLTRUE];
Orientation: TYPE = {cw, ccw, reverse};
SliceSetOrientationProc: TYPE = PROC [slice: Slice, parts: SliceParts, orientation: Orientation, history: HistoryEvent] RETURNS [success: BOOL];
SliceGetOrientationProc: TYPE = PROC [slice: Slice, parts: SliceParts] RETURNS [orientation: Orientation, isUnique: BOOLTRUE];
Outline Parts: Trajectories and Sequences
Traj: TYPE = Slice;
TrajData: TYPE = REF TrajDataObj; -- formerly Traj, now slice.data
TrajDataObj: TYPE = RECORD [ -- formerly TrajObj
role: FenceHoleOpen,
segCount: NAT, -- the number of segments currently in this trajectory
segments: Rosary.ROSARY, -- the segments themselves
Segments refer to joints (and other control points), and have drawing styles.
joints: Rosary.ROSARY, -- the segCount+1 joints at which the segments meet
Joints have a position and a continuity constraint
extraPoints: LIST OF Joint,
visibleJoints: BOOLTRUE,
strokeJoint: Imager.StrokeJoint ← round,
loArrow, hiArrow: BOOLFALSE,
forward: BOOLTRUE,
selectedInPart: SelectedObjectData,
polyline: GGSegmentTypes.PairSequence, -- a polyline approximation to this traj, for gravity
polylineTolerance: REAL
];
FenceHoleOpen: TYPE = {fence, hole, open, circle};
TrajEnd: TYPE = {lo, hi};
TrajPartType: TYPE = {none, joint, controlPoint, segment, interior};
Sequence: TYPE = SliceDescriptor;
TrajParts: TYPE = REF TrajPartsObj; -- formerly Sequence
TrajPartsObj: TYPE = RECORD [ -- formerly SequenceObj
segments: BitVector,
joints: BitVector,
controlPoints: BitMatrix, -- one BitVector per segment, one bit per CP per BitVector
segCount: NAT, -- the number of segments represented by this sequence
jointCount: NAT, -- the number of joints represented by this sequence
controlPointCount: NAT
];
Generators
SliceGenerator: TYPE = REF SliceGeneratorObj;
SliceGeneratorObj: TYPE = RECORD [
list: LIST OF Slice
];
SliceDescriptorGenerator: TYPE = REF SliceDescriptorGeneratorObj;
SliceDescriptorGeneratorObj: TYPE = RECORD [
list: LIST OF SliceDescriptor
];
SegmentGenerator: TYPE = REF SegmentGeneratorObj;
SegmentGeneratorObj: TYPE = RECORD [
traj: TrajData,
toGo: NAT,
index: NAT ← 0,
touched: NAT ← 0, -- # segments we have considered returning (should be <= segCount).
seq: TrajParts,
completeSeq: BOOLFALSE,
sliceD: SliceDescriptor,
classSpecific: REF ANY
];
JointGenerator: TYPE = REF JointGeneratorObj;
JointGeneratorObj: TYPE = RECORD [
traj: TrajData,
toGo: NAT,
index: NAT,
seq: TrajParts,
completeSeq: BOOLFALSE
];
ControlPointGenerator: TYPE = REF ControlPointGeneratorObj;
ControlPointGeneratorObj: TYPE = RECORD [
traj: TrajData,
seq: TrajParts,
toGo: NAT,
segIndex: NAT, -- together [segIndex, cpIndex] name the next control point to consider
cpIndex: NAT
];
PointGenerator: TYPE = REF PointGeneratorObj;
PointGeneratorObj: TYPE = RECORD [
sliceD: SliceDescriptor,
toGo: NAT,
index: NAT,
classSpecific: REF ANY
];
PointPairGenerator: TYPE = REF PointPairGeneratorObj;
PointPairGeneratorObj: TYPE = RECORD [
sliceD: SliceDescriptor,
toGo: NAT,
index: NAT,
classSpecific: REF ANY
];
BoundBoxGenerator: TYPE = REF BoundBoxGeneratorObj;
BoundBoxGeneratorObj: TYPE = RECORD [
list: LIST OF BoundBox
];
Gravity and Alignments
AlignmentObject: TYPE = REF ANY; -- types: AlignmentLine, AlignmentCircle, AlignmentPoint, SliceDescriptor, Sequence
FeatureData: TYPE = REF FeatureDataObj;
FeatureDataObj: TYPE = RECORD [
type: FeatureType,
shape: AlignmentObject
];
FeatureType: TYPE = {slice, distanceLine, slopeLine, angleLine, symmetryLine, radiiCircle, intersectionPoint, midpoint, anchor};
END.