DIRECTORY AtomButtonsTypes, CodeTimer, CoordSys, SVRay, DisplayListToTree, IO, Matrix3d, Preprocess3d, Real, SV2d, SV3d, SVAssembly, SVCastRays, SVGravity, SVInterfaceTypes, SVLines3d, SVModelTypes, SVRayTypes, SVScene, SVSceneTypes, SVState; SVGravityImpl: CEDAR PROGRAM IMPORTS CodeTimer, CoordSys, SVRay, DisplayListToTree, Matrix3d, Preprocess3d, SVAssembly, SVCastRays, SVLines3d, SVState EXPORTS SVGravity = BEGIN Slice: TYPE = SVSceneTypes.Slice; Camera: TYPE = SVSceneTypes.Camera; Classification: TYPE = SVRayTypes.Classification; CSGTree: TYPE = SVRayTypes.CSGTree; FeatureData: TYPE = SVInterfaceTypes.FeatureData; FeedbackData: TYPE = AtomButtonsTypes.FeedbackData; GravityType: TYPE = SVInterfaceTypes.GravityType; Line3d: TYPE = SV3d.Line3d; MasterObject: TYPE = SVSceneTypes.MasterObject; Matrix4by4: TYPE = SV3d.Matrix4by4; Point2d: TYPE = SV2d.Point2d; Point3d: TYPE = SV3d.Point3d; PointAndDone: TYPE = SVSceneTypes.PointAndDone; PointGenerator: TYPE = SVSceneTypes.PointGenerator; Primitive: TYPE = SVRayTypes.Primitive; Ray: TYPE = SVRayTypes.Ray; Scene: TYPE = SVSceneTypes.Scene; SearchDepth: TYPE = SVRayTypes.SearchDepth; Shape: TYPE = SVSceneTypes.Shape; SliceDescriptor: TYPE = SVSceneTypes.SliceDescriptor; TriggerBag: TYPE = SVInterfaceTypes.TriggerBag; Vector3d: TYPE = SV3d.Vector3d; SVData: TYPE = SVInterfaceTypes.SVData; RayMap: PUBLIC PROC [cameraPoint: Point2d, criticalR: REAL, alignBag: REF ANY, sceneBag: TriggerBag, svData: SVData] RETURNS [surfacePtWORLD: Point3d, normalWORLD: Vector3d, feature: FeatureData, hitData: REF ANY] = { gravityType: GravityType _ SVState.GetGravityType[svData]; searchDepth: SearchDepth _ SVState.GetSearchDepth[svData]; CodeTimer.StartInt[$RayMap, $Solidviews]; [surfacePtWORLD, normalWORLD, feature, hitData] _ PointsOrSurfaces[cameraPoint, criticalR, sceneBag, svData.camera, searchDepth, gravityType]; CodeTimer.StopInt[$RayMap, $Solidviews]; }; PointsPreferred: PUBLIC PROC [cameraPoint: Point2d, criticalR: REAL, alignBag: REF ANY, sceneBag: TriggerBag, svData: SVData, sceneOnly: BOOL] RETURNS [surfacePtWORLD: Point3d, normalWORLD: Vector3d, feature: FeatureData, hitData: REF ANY] = { RETURN RayMap[cameraPoint, criticalR, alignBag, sceneBag, svData]; }; StrictDistance: PUBLIC PROC [cameraPoint: Point2d, criticalR: REAL, alignBag: REF ANY, sceneBag: TriggerBag, svData: SVData, sceneOnly: BOOL] RETURNS [surfacePtWORLD: Point3d, normalWORLD: Vector3d, feature: FeatureData, hitData: REF ANY] = { RETURN RayMap[cameraPoint, criticalR, alignBag, sceneBag, svData]; }; PointsOrSurfaces: PUBLIC PROC [cameraPoint: Point2d, criticalR: REAL, sceneBag: TriggerBag, camera: Camera, searchDepth: SearchDepth, gravityType: GravityType] RETURNS [surfacePtWORLD: Point3d, normalWORLD: Vector3d, feature: FeatureData, hitData: REF ANY] = { pointsPtWORLD: Point3d; pointsNormalWORLD: Vector3d; pointsFeature: FeatureData; parallel: BOOL; pointsHitData: REF ANY; rayWORLD: Ray _ GetWorldRayFromCameraPoint[cameraPoint, camera]; -- from pool [surfacePtWORLD, normalWORLD, feature, hitData] _ RayAtSurfaces[rayWORLD, cameraPoint, criticalR, sceneBag, camera, searchDepth]; [pointsPtWORLD, pointsNormalWORLD, pointsFeature, pointsHitData] _ RayAtPoints[rayWORLD, cameraPoint, criticalR, sceneBag, camera, gravityType]; IF pointsFeature # NIL AND WithinTolerance[pointsPtWORLD, rayWORLD, criticalR] THEN { surfacePtWORLD _ pointsPtWORLD; IF pointsFeature # feature THEN { normalWORLD _ pointsNormalWORLD; feature _ pointsFeature; }; hitData _ pointsHitData; } ELSE IF feature # NIL THEN { } ELSE { [surfacePtWORLD, normalWORLD, parallel] _ RayMeetsCentralCameraPlane[cameraPoint, camera]; hitData _ NIL; }; SVRay.ReturnRayToPool[rayWORLD]; }; LineFromRay: PROC [ray: Ray] RETURNS [line: Line3d] = { basePt: Point3d; direction: Vector3d; [basePt, direction] _ SVRay.GetWorldRay[ray]; line _ SVLines3d.LineFromPointAndVector[basePt, direction]; }; WithinTolerance: PROC [point: Point3d, rayWORLD: Ray, criticalR: REAL] RETURNS [BOOL] = { line: Line3d; dist: REAL; line _ LineFromRay[rayWORLD]; dist _ SVLines3d.DistancePointToLine[point, line]; RETURN[dist <= criticalR]; }; GetWorldRayFromCameraPoint: PROC [cameraPoint: Point2d, camera: Camera] RETURNS [rayWORLD: Ray] = { rayCamera: Ray; cameraWORLD: Matrix4by4 _ CoordSys.WRTWorld[camera.coordSys]; rayCamera _ SVRay.GetRayFromPool[]; SVRay.StuffCameraRay[rayCamera, cameraPoint, camera]; rayWORLD _ SVRay.TransformRayToWorld[rayCamera, cameraWORLD]; -- allocates ray from pool SVRay.ReturnRayToPool[rayCamera]; }; RayAtSurfaces: PROC [rayWorld: Ray, cameraPoint: Point2d, criticalR: REAL, sceneBag: TriggerBag, camera: Camera, searchDepth: SearchDepth] RETURNS [surfacePtWorld: Point3d, normalWorld: Vector3d, feature: FeatureData, hitData: REF ANY] = { class: Classification; primitive: Primitive; assembly: Slice; class _ SingleRay[rayWorld, cameraPoint, sceneBag, camera, TRUE, NIL]; -- class from pool IF sceneBag.scene # NIL THEN [assembly, primitive] _ AssemblyAndPrimitiveAtSearchDepth[class, searchDepth, sceneBag.scene.assembly]; IF class.count > 0 THEN [surfacePtWorld, normalWorld] _ SurfacePointAndNormalAtSearchDepth[class, rayWorld, searchDepth, sceneBag.scene.assembly]; feature _ FindFeature[assembly, sceneBag]; hitData _ HitDataAtSearchDepth[class, searchDepth, sceneBag.scene.assembly]; SVCastRays.ReturnClassToPool[class]; }; FindFeature: PROC [assembly: Slice, sceneBag: TriggerBag] RETURNS [feature: FeatureData] = { sliceD: SliceDescriptor; IF assembly = NIL THEN RETURN[NIL]; FOR list: LIST OF FeatureData _ sceneBag.slices, list.rest UNTIL list = NIL DO sliceD _ NARROW[list.first.shape]; IF sliceD.slice = assembly THEN RETURN[list.first]; ENDLOOP; RETURN[NIL]; }; AssemblyAndPrimitiveAtSearchDepth: PROC [class: Classification, searchDepth: SearchDepth, root: Slice] RETURNS [assembly: Slice, primitive: Primitive] = { SELECT searchDepth FROM first => [assembly, primitive] _ SVCastRays.NthAssemblyAndPrimitive[class, 1]; lastOfFirst => [assembly, primitive] _ SVCastRays.NthAssemblyAndPrimitive[class, 1]; last => [assembly, primitive] _ SVCastRays.NthAssemblyAndPrimitive[class, class.count]; lastOfLevel1 => [assembly, primitive] _ SVCastRays.LastTopLevelAssemAndPrim[class, root]; ENDCASE => ERROR; }; SurfacePointAndNormalAtSearchDepth: PROC [class: Classification, rayWorld: Ray, searchDepth: SearchDepth, root: Slice] RETURNS [surfacePtWorld: Point3d, normalWorld: Vector3d] = { SELECT searchDepth FROM first => [surfacePtWorld, normalWorld] _ SVCastRays.NthSurfacePointAndNormal[class, rayWorld, 1]; lastOfFirst => [surfacePtWorld, normalWorld] _ SVCastRays.LastOfFirstPointAndNormal[class, rayWorld]; last => IF class.count = 0 THEN ERROR ELSE [surfacePtWorld, normalWorld] _ SVCastRays.NthSurfacePointAndNormal[class, rayWorld, class.count]; lastOfLevel1 => [surfacePtWorld, normalWorld] _ SVCastRays.LastTopLevelPointAndNormal[class, rayWorld, root]; ENDCASE => ERROR; }; HitDataAtSearchDepth: PROC [class: Classification, searchDepth: SearchDepth, root: Slice] RETURNS [hitData: REF ANY] = { SELECT searchDepth FROM first => hitData _ SVCastRays.NthHitData[class, 1]; lastOfFirst => hitData _ SVCastRays.LastOfFirstHitData[class]; last => IF class.count = 0 THEN ERROR ELSE hitData _ SVCastRays.NthHitData[class, class.count]; lastOfLevel1 => hitData _ SVCastRays.LastTopLevelHitData[class, root]; ENDCASE => ERROR; }; SingleRay: PUBLIC PROC [rayWorld: Ray, cameraPoint: Point2d, sceneBag: TriggerBag, camera: Camera, consolidate: BOOL _ TRUE, feedback: FeedbackData, makeStream: BOOL _ FALSE] RETURNS [class: Classification] = { tree: CSGTree _ sceneBag.tree; topNode: REF ANY; IF tree = NIL THEN { class _ SVCastRays.GetClassFromPool[]; SVCastRays.MakeClassAMiss[class]; RETURN; }; IF tree.outOfDate THEN { tree _ DisplayListToTree.AssemblyToTree[sceneBag.scene.assembly, sceneBag.scene, camera, tree]; [] _ Preprocess3d.PreprocessForInteraction[tree, camera]; tree.outOfDate _ FALSE; }; topNode _ tree.son; class _ SVCastRays.RayCast[cameraPoint, rayWorld, topNode, consolidate, feedback, makeStream, 0]; }; -- end of SingleRay RayAtPoints: PROC [ray: Ray, cameraPoint: Point2d, criticalR: REAL, sceneBag: TriggerBag, camera: Camera, gravityType: GravityType] RETURNS [bestPoint: Point3d, bestNormal: Vector3d, bestFeature: FeatureData, bestHitData: REF ANY] = { line3d: Line3d; bestDist, thisDist: REAL; pointWORLD: Point3d; feature: FeatureData; sliceD: SliceDescriptor; hitData: REF ANY; success: BOOL; scene: Scene _ sceneBag.scene; line3d _ LineFromRay[ray]; bestDist _ Real.LargestNumber; bestFeature _ NIL; IF gravityType = linesPreferred THEN { FOR list: LIST OF FeatureData _ sceneBag.slices, list.rest UNTIL list = NIL DO feature _ list.first; sliceD _ NARROW[feature.shape]; [thisDist, pointWORLD, hitData, success] _ SVAssembly.ClosestSegmentToLine[sliceD, cameraPoint, line3d, criticalR, camera]; IF success AND thisDist < bestDist THEN { bestDist _ thisDist; bestPoint _ pointWORLD; bestHitData _ hitData; bestFeature _ feature; }; ENDLOOP; }; FOR list: LIST OF FeatureData _ sceneBag.slices, list.rest UNTIL list = NIL DO feature _ list.first; sliceD _ NARROW[feature.shape]; [thisDist, pointWORLD, hitData, success] _ SVAssembly.ClosestPointToLine[sliceD, cameraPoint, line3d, criticalR, camera]; IF success AND thisDist < bestDist THEN { bestDist _ thisDist; bestPoint _ pointWORLD; bestHitData _ hitData; bestFeature _ feature; }; ENDLOOP; bestNormal _ Matrix3d.ZAxisOfMatrix[CoordSys.WRTWorld[camera.coordSys]]; }; RayMeetsCameraPlane: PROC [cameraPoint: Point2d, depth: REAL, camera: Camera] RETURNS [planePtCamera: Point3d, parallel: BOOL] = { rayWorld: Ray; worldCamera: Matrix4by4; planePtWorld: Point3d; rayWorld _ SVRay.GetRayFromPool[]; SVRay.StuffWorldRayFromCamera[rayWorld, cameraPoint, camera]; [planePtWorld, parallel] _ SVCastRays.RayMeetsPlaneOfCoordSystem[camera.coordSys, rayWorld, 3, depth]; worldCamera _ CoordSys.FindAInTermsOfB[CoordSys.Parent[camera.coordSys], camera.coordSys]; planePtCamera _ Matrix3d.Update[planePtWorld, worldCamera]; SVRay.ReturnRayToPool[rayWorld]; }; RayMeetsCentralCameraPlane: PROC [cameraPoint: Point2d, camera: Camera] RETURNS [pointWORLD: Point3d, normalWORLD: Vector3d, parallel: BOOL] = { worldCAMERA: Matrix4by4 _ CoordSys.FindWorldInTermsOf[camera.coordSys]; originCAMERA: Point3d _ Matrix3d.OriginOfMatrix[worldCAMERA]; depth: REAL _ originCAMERA[3]; rayWorld: Ray; rayWorld _ SVRay.GetRayFromPool[]; SVRay.StuffWorldRayFromCamera[rayWorld, cameraPoint, camera]; [pointWORLD, parallel] _ SVCastRays.RayMeetsPlaneOfCoordSystem[camera.coordSys, rayWorld, 3, depth]; normalWORLD _ Matrix3d.ZAxisOfMatrix[CoordSys.WRTWorld[camera.coordSys]]; SVRay.ReturnRayToPool[rayWorld]; }; InitStats: PROC = { interval: CodeTimer.Interval; interval _ CodeTimer.CreateInterval[$RayMap]; CodeTimer.AddInt[interval, $Solidviews]; }; InitStats[]; END. æSVGravityImpl.mesa Copyright c 1986 by Xerox Corporation. All rights reserved. Last edited by Bier on February 17, 1987 11:19:15 pm PST Contents: Routines to snap the skitter to faces, segments, and points in the scene. Ê ]˜J˜Icodešœ™Kšœ Ïmœ1™˜ZKšœ žœ˜K˜—Kšžœ œ˜ K˜K˜—K˜šŸ œžœ žœ˜7Kšœ˜Kšœ˜Kšœžœ˜-Kšœ;˜;K˜K˜—š Ÿœžœ œžœžœžœ˜YKšœ ˜ Kšœžœ˜ Kšœ œ˜Kšœ2˜2Kšžœ˜K˜K˜—šŸœžœ(žœ œ ˜cIprocšœ œ˜Lšœ œ2˜=Lšœ œžœ˜#Lšžœ œ˜5Lš œ œžœ œ œÏc˜XLšžœ œ˜!K˜K˜—š Ÿ œžœ2žœBžœQžœžœ˜ïJšœ˜Jšœ˜J˜J˜Jšœ;žœžœ¢˜Yšžœžœž˜Jšœg˜g—šžœž˜Jšœ  œ œ1 œ(˜z—Jšœ*˜*JšœL˜LJšœ$˜$K˜K˜—šŸ œžœ)žœ˜\Jšœ˜Jš žœ žœžœžœžœ˜#š žœžœžœ*žœžœž˜NJšœ žœ˜"Jšžœžœžœ ˜3Jšžœ˜—Jšžœžœ˜ J˜J˜—šÐbnŸ œžœ@žœ,˜šJšžœ ž˜Jšœ,¡œ ˜NJšœ2¡œ ˜TJšœ+¡œ˜WJšœ3¡œ˜YJšžœžœ˜J˜J˜—š £Ÿ œžœ œ.žœ  œ œ˜³Jšžœ ž˜šœ˜Jš œ  œ œ¡œ  œ˜X—šœ˜Jš œ  œ œ¡œ  œ˜V—šœ˜Jšžœžœž˜Jš žœ  œ œ¡œ  œ˜g—šœ˜Jš œ  œ œ¡œ  œ˜]—Jšžœžœ˜J˜J˜—š Ÿœžœ@žœ žœžœ˜xJšžœ ž˜šœ˜Jšœ*˜*—šœ˜Jšœ/˜/—šœ˜Jšžœžœž˜Jšžœ5˜9—šœ˜Jšœ6˜6—Jšžœžœ˜J˜J˜—šŸ œžœžœZžœžœ&žœžœžœ˜ÒLšœ˜Lšœ žœž˜J˜šžœžœžœ˜Jšœ&˜&Jšœ!˜!Jšžœ˜J˜—šžœžœ˜Jšœ_˜_Jšœ9˜9Jšœžœ˜J˜J˜—Lšœ˜Lšœ+ œ1˜aLšœ¢˜—K˜š Ÿ œžœ-žœBžœSžœžœ˜êKšœ˜Kšœžœ˜Kšœ œ ˜Kšœ˜K˜Kšœ žœžœ˜Kšœ žœ˜Kšœ˜K˜Kšœ˜Kšœ˜Kšœžœ˜šžœžœ˜&š žœžœžœ*žœžœž˜NKšœ˜Kšœ žœ˜Kšœ œf˜{šžœ žœžœ˜)Kšœ˜Kšœ œ˜Kšœ˜Kšœ˜K˜—Kšžœ˜—K˜—š žœžœžœ*žœžœž˜NKšœ˜Kšœ žœ˜Kšœ œd˜yšžœ žœžœ˜)Kšœ˜Kšœ œ˜Kšœ˜Kšœ˜K˜—Kšžœ˜—KšœH˜HK˜K˜—K˜š Ÿœžœžœžœ  œžœ˜‚Jšœ œ˜Jšœ œ ˜Jšœ œ ˜Jšœ œžœ˜"Jšžœ œ˜=Jšœ œH œ ˜fJšœ œO˜ZJšœ œ œ œ˜;Jšžœ œ˜ J˜J˜—š Ÿœžœ(žœ œ œžœ˜Kšœ œ<˜GKšœ œ) œ˜=Kšœžœ  œ˜Jšœ œ˜Jšœ œžœ˜"Jšžœ œ˜=Jšœ œH œ ˜dKšœ œ>˜IJšžœ œ˜ K˜—K˜šŸ œžœ˜K˜Kšœ-˜-Kšœ(˜(K˜K˜—K˜ Kšžœ˜K˜J˜—…—*”6×