コード例 #1
0
ファイル: DynamicSnapSolver.cs プロジェクト: tomleetv/gsCore
        // returns snapped world-frame, or input frame if no snap
        public Frame3f UpdateSnapW(Frame3f fSourceFrameW, SnapSet Snaps)
        {
            FScene scene        = targetSO.GetScene();
            float  fSnapRadiusW = VRUtil.GetVRRadiusForVisualAngle(fSourceFrameW.Origin,
                                                                   scene.ActiveCamera.GetPosition(), SnapThreshVisualAngleDeg);
            float fSnapRadiusS = fSnapRadiusW / scene.GetSceneScale();

            // fSourceFrameW in Scene coordinates
            Frame3f fSourceS = scene.ToSceneFrame(fSourceFrameW);

            SnapResult best_snap    = null;
            float      fNearest     = float.MaxValue;
            Frame3f    fBestSourceL = Frame3f.Identity;

            // snapframes are stored in local coords relative to object
            foreach (Frame3f fPointFrameL in snapFramesL)
            {
                // convert local-coord snap frame into scene coords
                Frame3f fPointFrameS = fSourceS.FromFrame(fPointFrameL);

                SnapResult snap = Snaps.FindNearestSnapPointS(fPointFrameS, fSnapRadiusS);
                if (snap != null)
                {
                    float d = ((Vector3f)snap.FrameS.Origin - fPointFrameS.Origin).Length;
                    if (d < fNearest)
                    {
                        fNearest     = d;
                        fBestSourceL = fPointFrameL;
                        best_snap    = snap;
                    }
                }
            }

            snapState.UpdateState(best_snap, fBestSourceL);
            if (snapState.IsSnapped)
            {
                SnapResult useSnap    = snapState.ActiveSnapTarget;
                Frame3f    useSourceL = (Frame3f)snapState.ActiveSnapData;

                if (SnapOrientation)
                {
                    // compute min-rotation frame, then align origins
                    Frame3f fAlignedSourceS =
                        Frame3f.SolveMinRotation(fSourceS, useSnap.FrameS);
                    Frame3f  fPointFrameS = fAlignedSourceS.FromFrame(useSourceL);
                    Vector3f deltaS       = (Vector3f)useSnap.FrameS.Origin - fPointFrameS.Origin;
                    snapFrameS = fAlignedSourceS.Translated(deltaS);


                    //// this is tricky...we have an object-space frame useSourceL, which
                    ////  we want to snap to a scene-space frame usePoint.FrameS. So we need
                    ////  to shift origin of that frame by -useSourceL_in_FrameS!
                    //snapFrameS = usePoint.FrameS.Translated(
                    //    -usePoint.FrameS.FromFrameV(useSourceL.Origin));
                }
                else
                {
                    // translation-only snap - find shift in scene space, apply to input source frame
                    Frame3f  fPointFrameS = fSourceS.FromFrame(useSourceL);
                    Vector3f deltaS       = (Vector3f)useSnap.FrameS.Origin - fPointFrameS.Origin;
                    snapFrameS = fSourceS.Translated(deltaS);
                }

                // now convert to world frame for return
                return(scene.ToWorldFrame(snapFrameS));
            }

            return(fSourceFrameW);
        }
コード例 #2
0
        public override bool UpdateCapture(ITransformable target, Ray3f worldRay)
        {
            // find hit
            SnapResult snap = Targets.FindHitSnapPoint(worldRay);

            snapState.UpdateState(snap);

            if (snapState.IsSnapped)
            {
                SnapResult useSnap   = snapState.ActiveSnapTarget;
                Frame3f    hitFrameS = Frame3f.Identity;
                if (useSnap != null)
                {
                    hitFrameS = new Frame3f(useSnap.FrameS);
                }

                Frame3f targetF = originalTargetS; // target.GetLocalFrame(CoordSpace.WorldCoords);
                Frame3f pivotF  = hitFrameS;
                targetF.Origin = pivotF.Origin;

                if (parent.CurrentFrameMode == FrameType.WorldFrame)
                {
                    targetF.Rotation = Quaternion.identity;
                }
                else
                {
                    targetF.Rotation = pivotF.Rotation;
                }

                Vector3f deltaInT = targetF.FromFrameV(SourceFrameL.Origin);
                targetF.Origin -= deltaInT;   // why is this minus?

                target.SetLocalFrame(targetF, CoordSpace.SceneCoords);
            }
            else
            {
                Func <SceneObject, bool> filter = null;
                if (TargetObjects != null && TargetObjects.Count > 0)
                {
                    filter = (x) => { return(TargetObjects.Contains(x) == false); }
                }
                ;

                AnyRayHit hit;
                if (scene.FindSceneRayIntersection(worldRay, out hit, true, filter))
                {
                    Vector3f hitPosS  = scene.ToSceneP(hit.hitPos);
                    Vector3f hitNormS = scene.ToSceneN(hit.hitNormal);

                    Frame3f targetF = originalTargetS;
                    targetF.Origin = hitPosS;
                    targetF.AlignAxis(1, hitNormS);

                    if (parent.CurrentFrameMode == FrameType.WorldFrame)
                    {
                        targetF.Rotation = Quaternion.identity;
                    }

                    Vector3f deltaInT = targetF.FromFrameV(SourceFrameL.Origin);
                    targetF.Origin -= deltaInT;   // why is this minus?
                    target.SetLocalFrame(targetF, CoordSpace.SceneCoords);
                }
                else
                {
                    target.SetLocalFrame(originalTargetS, CoordSpace.SceneCoords);
                }
            }

            return(true);
        }