Ejemplo n.º 1
0
        public static Transform GetUserSRSToModelTransform(OSGeo.OSR.SpatialReference userSRS)
        {
            ///TODO: Check what units the userSRS is in and coordinate with the scaling function.  Currently only accounts for a userSRS in meters.
            ///TODO: translate or scale GCS (decimal degrees) to something like a Projectected Coordinate System.  Need to go dd to xy

            ///transform rhino EAP from rhinoSRS to userSRS
            double eapLat   = EarthAnchorPoint.EarthBasepointLatitude;
            double eapLon   = EarthAnchorPoint.EarthBasepointLongitude;
            double eapElev  = EarthAnchorPoint.EarthBasepointElevation;
            Plane  eapPlane = EarthAnchorPoint.GetEarthAnchorPlane(out Vector3d eapNorth);

            OSGeo.OSR.SpatialReference rhinoSRS = new OSGeo.OSR.SpatialReference("");
            rhinoSRS.SetWellKnownGeogCS("WGS84");

            OSGeo.OSR.CoordinateTransformation coordTransform = new OSGeo.OSR.CoordinateTransformation(rhinoSRS, userSRS);
            OSGeo.OGR.Geometry userAnchorPointDD = Heron.Convert.Point3dToOgrPoint(new Point3d(eapLon, eapLat, eapElev));
            Transform          t = new Transform(1.0);

            userAnchorPointDD.Transform(coordTransform);

            Point3d userAnchorPointPT = Heron.Convert.OgrPointToPoint3d(userAnchorPointDD, t);

            ///setup userAnchorPoint plane for move and rotation
            double eapLatNorth = EarthAnchorPoint.EarthBasepointLatitude + 0.5;
            double eapLonEast  = EarthAnchorPoint.EarthBasepointLongitude + 0.5;

            OSGeo.OGR.Geometry userAnchorPointDDNorth = Heron.Convert.Point3dToOgrPoint(new Point3d(eapLon, eapLatNorth, eapElev));
            OSGeo.OGR.Geometry userAnchorPointDDEast  = Heron.Convert.Point3dToOgrPoint(new Point3d(eapLonEast, eapLat, eapElev));
            userAnchorPointDDNorth.Transform(coordTransform);
            userAnchorPointDDEast.Transform(coordTransform);
            Point3d  userAnchorPointPTNorth = Heron.Convert.OgrPointToPoint3d(userAnchorPointDDNorth, t);
            Point3d  userAnchorPointPTEast  = Heron.Convert.OgrPointToPoint3d(userAnchorPointDDEast, t);
            Vector3d userAnchorNorthVec     = userAnchorPointPTNorth - userAnchorPointPT;
            Vector3d userAnchorEastVec      = userAnchorPointPTEast - userAnchorPointPT;

            Plane userEapPlane = new Plane(userAnchorPointPT, userAnchorEastVec, userAnchorNorthVec);

            ///shift (move and rotate) from userSRS EAP to 0,0 based on SRS north direction
            Transform scale = Transform.Scale(new Point3d(0.0, 0.0, 0.0), (1 / Rhino.RhinoMath.UnitScale(Rhino.RhinoDoc.ActiveDoc.ModelUnitSystem, Rhino.UnitSystem.Meters)));

            if (userSRS.GetLinearUnitsName().ToUpper().Contains("FEET") || userSRS.GetLinearUnitsName().ToUpper().Contains("FOOT"))
            {
                scale = Transform.Scale(new Point3d(0.0, 0.0, 0.0), (1 / Rhino.RhinoMath.UnitScale(Rhino.RhinoDoc.ActiveDoc.ModelUnitSystem, Rhino.UnitSystem.Feet)));
            }

            ///if SRS is geographic (ie WGS84) use Rhino's internal projection
            ///this is still buggy as it doesn't work with other geographic systems like NAD27
            if ((userSRS.IsProjected() == 0) && (userSRS.IsLocal() == 0))
            {
                userEapPlane.Transform(WGSToXYZTransform());
                scale = WGSToXYZTransform();
            }

            Transform shift = Transform.ChangeBasis(eapPlane, userEapPlane);

            Transform shiftScale = Transform.Multiply(scale, shift);

            return(shiftScale);
        }