精华内容
下载资源
问答
  • UTM 坐标转换

    2015-06-10 23:27:41
    UTM坐标转换大地坐标系转换,详细介绍了UTM到大地坐标系的转换方法,地理信息工作者适用
  • 计算UTM坐标转换为经纬度坐标 根据UTM定义 Excel表格自动计算 输入UTM坐标参数,自动计算并且输出经纬度坐标 Excel表格自动计算 输入UTM坐标参数,自动计算并且输出经纬度坐标 Excel表格自动计算 输入UTM坐标参数...
  • UTM坐标转换大地坐标系转换,详细介绍了UTM到大地坐标系的转换方法,地理信息工作者适用
  • 通过这个小程序,你可以得到UTM坐标到球坐标的变换或转换,你可以选择不同的椭球来执行转换。 2. 输入: x、y、utm 区域和半球。 3. 输出: 纬度、经度和经度的参考。 4.注意事项: 只需要运行该函数。 我设计的...
  • 坐标转换matlab代码MATLAB-GPS-计算 这是一个计算 Mercantor 投影和 UTM 坐标转换的函数列表,以便使用基于相对笛卡尔的坐标系。 这是我在 Audi AG 实习时开发的功能列表。 本项目中使用的墨卡托投影背后的数学和...
  • UTM投影是GoogleEarh采用的一种投影,它与大地坐标转换在外国工程利用中特别频繁。该软件实现了这种转换,单文件绿色免费,实现精度为几个纳米级。
  • 此函数显示一个窗口(一个小 GUI),您可以使用该窗口将经纬度坐标转换UTM 坐标。 您可以选择不同的椭球体来执行转换。 [ x,y,utmzone ] = UTM(instruccion) 输入: 纬度、经度坐标。 输出: X, Y , Utm 区。 ...
  • 经纬度与高斯坐标及经纬度与UTM坐标互转,有需要的可以下载一下啊!函数切实好用,通过global mapper验证,证明其是准确的。
  • 此函数基于 Gabriel Ruiz Martinez 的 UTMIP.m 函数,但它不提供 GUI,而是使用坐标向量。 [纬度,经度] = utm2deg(x,y,utmzone) % 示例 1: % x=[ 458731; 407653; 239027; 230253; 343898; 362850]; % y=...
  • c#代码 utm坐标转换经纬度坐标 根据地球半径计算经纬度 public static void UTMToLatLon(double utmX, double utmY, out double latitude, out double longitude) { bool isNorthHemisphere = true; var diflat ...

    c#代码 utm坐标转换经纬度坐标

    根据地球半径计算经纬度

     public static void UTMToLatLon(double utmX, double utmY, out double latitude, out double longitude)
    {
        bool isNorthHemisphere = true;
    
        var diflat = 4.00372863181963E-07;
        var diflon = -6.88086842459646E-08;
    
    
        var zone = 51;
        var c_sa = 6378137.000000;
        var c_sb = 6356752.314245;
        var e2 = Math.Pow((Math.Pow(c_sa, 2) - Math.Pow(c_sb, 2)), 0.5) / c_sb;
        var e2cuadrada = Math.Pow(e2, 2);
        var c = Math.Pow(c_sa, 2) / c_sb;
        var x = utmX - 500000;
        var y = isNorthHemisphere ? utmY : utmY - 10000000;
        var s = ((zone * 6.0) - 183.0);
        var lat = y / (c_sa * 0.9996);
        var v = (c / Math.Pow(1 + (e2cuadrada * Math.Pow(Math.Cos(lat), 2)), 0.5)) * 0.9996;
        var a = x / v;
        var a1 = Math.Sin(2 * lat);
        var a2 = a1 * Math.Pow((Math.Cos(lat)), 2);
        var j2 = lat + (a1 / 2.0);
        var j4 = ((3 * j2) + a2) / 4.0;
        var j6 = ((5 * j4) + Math.Pow(a2 * (Math.Cos(lat)), 2)) / 3.0;
        var alfa = (3.0 / 4.0) * e2cuadrada;
        var beta = (5.0 / 3.0) * Math.Pow(alfa, 2);
        var gama = (35.0 / 27.0) * Math.Pow(alfa, 3);
        var bm = 0.9996 * c * (lat - alfa * j2 + beta * j4 - gama * j6);
        var b = (y - bm) / v;
        var epsi = ((e2cuadrada * Math.Pow(a, 2)) / 2.0) * Math.Pow((Math.Cos(lat)), 2);
        var eps = a * (1 - (epsi / 3.0));
        var nab = (b * (1 - epsi)) + lat;
        var senoheps = (Math.Exp(eps) - Math.Exp(-eps)) / 2.0;
        var delt = Math.Atan(senoheps / (Math.Cos(nab)));
        var tao = Math.Atan(Math.Cos(delt) * Math.Tan(nab));
    
        longitude = ((delt * (180.0 / Math.PI)) + s) + diflon;
        latitude = ((lat + (1 + e2cuadrada * Math.Pow(Math.Cos(lat), 2) - (3.0 / 2.0) * e2cuadrada * Math.Sin(lat) * Math.Cos(lat) * (tao - lat)) * (tao - lat)) * (180.0 / Math.PI)) + diflat;
    }
    
    展开全文
  • 此函数基于 Gabriel Ruiz Martinez 的 UTM.m 函数,但它不提供 GUI,而是使用坐标向量。 [x,y,utmzone] = deg2utm(Lat,Lon) % 示例 1: % 纬度=[40.3154333; 46.283900; 37.577833; 28.645650; 38.855550; 25....
  • C# UTM坐标和WGS84坐标转换工具及源码 工具路径:UTMAndWGS84TransTool\UTMAndWGS84TransTool\bin\Debug\UTMAndWGS84TransTool.exe
  • GPS经纬度坐标和UTM坐标的相互转换

    千次阅读 2020-07-22 16:25:33
    UTM坐标系介绍 我们在地理课上学过用经纬度表示在地球上的坐标,这种表示方法适合在一个三维的地球曲面上描述一个坐标,但是如果我们想在二维的平面上描述一个地理坐标应该怎么做呢? 1. 首先是将地球曲面投影到...

    UTM坐标系介绍

    我们在地理课上学过用经纬度表示在地球上的坐标,这种表示方法适合在一个三维的地球曲面上描述一个坐标,但是如果我们想在二维的平面上描述一个地理坐标应该怎么做呢? 

    1. 首先是将地球曲面投影到平面上

    如下图在地球中心为投影中心,向圆柱形进行射线的投影,然后将圆柱形的侧面进行展开,就可以得到一个平面投影的坐标。

    在这里插入图片描述

    如下图所示就是一幅世界的平面地图,正如我们平时看到的地图

    在这里插入图片描述

    2.将平面分成许多个cell,叫做zone

    如下图,分成了n个网格,以向东的方向为x轴,向北的方向为y轴,建立坐标系,每个小格子的中间的x坐标值都是500,000m

    在这里插入图片描述

    因为地球的是圆的,因此每个格子x轴方向的长度是不一样的,如下图

    在这里插入图片描述

    北方向是从南极指向北极,以赤道为分界线,坐标变化为0mS-1,000,000mS,再到0mN-1,000,000mN。其中S和N分别代表南半球和北半球,单位为:m

    在这里插入图片描述

    UTM的东北坐标只有两个数字,还需要zone的区间号才能转换为经纬度坐标因此准确的UTM坐标包括三个参数,区间+东北坐标。如下图

    在这里插入图片描述

    从经纬度转换为UTM坐标的E,N,然后zone编号就得到了唯一的UTM坐标了

    转换代码

    经纬度转UTM坐标的代码如下

    void LonLat2UTM(double longitude, double latitude, double& UTME, double& UTMN)
    {
    	double lat = latitude;
    	double lon = longitude;
    
    	double kD2R = PI / 180.0;
    	double ZoneNumber = floor((lon - 1.5) / 3.0) + 1;
    	double L0 = ZoneNumber * 3.0;
    
    	double a = 6378137.0;
    	double F = 298.257223563;
    	double f = 1 / F;
    	double b = a * (1 - f);
    	double ee = (a * a - b * b) / (a * a);
    	double e2 = (a * a - b * b) / (b * b);
    	double n = (a - b) / (a + b); 
    	double n2 = (n * n); 
    	double n3 = (n2 * n); 
    	double n4 = (n2 * n2); 
    	double n5 = (n4 * n);
    	double al = (a + b) * (1 + n2 / 4 + n4 / 64) / 2.0;
    	double bt = -3 * n / 2 + 9 * n3 / 16 - 3 * n5 / 32.0;
    	double gm = 15 * n2 / 16 - 15 * n4 / 32;
    	double dt = -35 * n3 / 48 + 105 * n5 / 256;
    	double ep = 315 * n4 / 512;
    	double B = lat * kD2R;
    	double L = lon * kD2R;
    	L0 = L0 * kD2R;
    	double l = L - L0; 
    	double cl = (cos(B) * l); 
    	double cl2 = (cl * cl); 
    	double cl3 = (cl2 * cl); 
    	double cl4 = (cl2 * cl2); 
    	double cl5 = (cl4 * cl); 
    	double cl6 = (cl5 * cl); 
    	double cl7 = (cl6 * cl); 
    	double cl8 = (cl4 * cl4);
    	double lB = al * (B + bt * sin(2 * B) + gm * sin(4 * B) + dt * sin(6 * B) + ep * sin(8 * B));
    	double t = tan(B); 
    	double t2 = (t * t); 
    	double t4 = (t2 * t2); 
    	double t6 = (t4 * t2);
    	double Nn = a / sqrt(1 - ee * sin(B) * sin(B));
    	double yt = e2 * cos(B) * cos(B);
    	double N = lB;
    	N = N + t * Nn * cl2 / 2;
    	N = N + t * Nn * cl4 * (5 - t2 + 9 * yt + 4 * yt * yt) / 24;
    	N = N + t * Nn * cl6 * (61 - 58 * t2 + t4 + 270 * yt - 330 * t2 * yt) / 720;
    	N = N + t * Nn * cl8 * (1385 - 3111 * t2 + 543 * t4 - t6) / 40320;
    	double E = Nn * cl;
    	E = E + Nn * cl3 * (1 - t2 + yt) / 6;
    	E = E + Nn * cl5 * (5 - 18 * t2 + t4 + 14 * yt - 58 * t2 * yt) / 120;
    	E = E + Nn * cl7 * (61 - 479 * t2 + 179 * t4 - t6) / 5040;
    	E = E + 500000;
    	N = 0.9996 * N;
    	E = 0.9996 * (E - 500000.0) + 500000.0;
    
    	UTME = E;
    	UTMN = N;
    }

    相关网站

    如下两个网站可用于经纬度坐标和UTM坐标的转换

    http://home.hiwaay.net/~taylorc/toolbox/geography/geoutm.html

    https://coordinates-converter.com/en/decimal/51.000000,10.000000?karte=OpenStreetMap&zoom=8

    展开全文
  • GPS坐标与UTM坐标转换

    千次阅读 热门讨论 2019-12-03 11:35:28
    将经纬度坐标转换UTM坐标。 1.3 订阅的话题 fix ( sensor_msgs/NavSatFix ):GPS测量和状态 1.4 发布的话题 odom ( nav_msgs/Odometry ):UTM编码的位置 1.5 参数 ~rot_covariance (double, ...

    1 简介

    1.1 消息

    gps_common定义了两个通用消息,供GPS驱动程序输出:gps_common/GPSFixgps_common/GPSStatus

    在大多数情况下,这些消息应同时发布,并带有相同的时间戳。

    1.2 utm_odometry_node节点

    utm_odometry_node将经纬度坐标转换为UTM坐标。

    1.3 订阅的话题

    fix (sensor_msgs/NavSatFix):GPS测量和状态

    1.4 发布的话题

    odom (nav_msgs/Odometry):UTM编码的位置

    1.5 参数

    • ~rot_covariance (double, default: 99999):指定旋转测量的方差(以米为单位)
    • ~frame_id (string, default: Copy frame_id from fix message): Frame to specify in header of outgoing Odometry message
    • ~child_frame_id (string): Child frame to specify in header of outgoing Odometry message

    2 安装

    mkdir -p ~/gps_ws/src
    cd ~/gps_ws/src
    git clone https://github.com/swri-robotics/gps_umd.git
    cd ..
    catkin_make
    

    报错:

    CMake Error at /usr/share/cmake-3.5/Modules/FindPkgConfig.cmake:367 (message):
    A required package was not found
    Call Stack (most recent call first):
    /usr/share/cmake-3.5/Modules/FindPkgConfig.cmake:532 (_pkg_check_modules_internal)
    gps_umd/gpsd_client/CMakeLists.txt:15 (pkg_check_modules)

    – Configuring incomplete, errors occurred!

    解决办法:

    sudo apt-get install libgps-dev
    

    最后,重新编译:

    catkin_make
    

    3 GPS坐标与UTM坐标的转换

    先写这个,个人认为用得比较多。

    3.1 GPS坐标转换为UTM坐标

    源文件utm_odometry_node.cpp:

    /*
     * Translates sensor_msgs/NavSat{Fix,Status} into nav_msgs/Odometry using UTM
     */
    
    #include <ros/ros.h>
    #include <message_filters/subscriber.h>
    #include <message_filters/time_synchronizer.h>
    #include <sensor_msgs/NavSatStatus.h>
    #include <sensor_msgs/NavSatFix.h>
    #include <gps_common/conversions.h>
    #include <nav_msgs/Odometry.h>
    
    using namespace gps_common;
    
    static ros::Publisher odom_pub;
    std::string frame_id, child_frame_id;
    double rot_cov;
    bool append_zone = false;
    
    void callback(const sensor_msgs::NavSatFixConstPtr& fix) {
      if (fix->status.status == sensor_msgs::NavSatStatus::STATUS_NO_FIX) {
        ROS_DEBUG_THROTTLE(60,"No fix.");
        return;
      }
    
      if (fix->header.stamp == ros::Time(0)) {
        return;
      }
    
      double northing, easting;
      std::string zone;
    
      LLtoUTM(fix->latitude, fix->longitude, northing, easting, zone);
    
      if (odom_pub) {
        nav_msgs::Odometry odom;
        odom.header.stamp = fix->header.stamp;
    
        if (frame_id.empty()) {
          if(append_zone) {
            odom.header.frame_id = fix->header.frame_id + "/utm_" + zone;
          } else {
            odom.header.frame_id = fix->header.frame_id;
          }
        } else {
          if(append_zone) {
            odom.header.frame_id = frame_id + "/utm_" + zone;
          } else {
            odom.header.frame_id = frame_id;
          }
        }
    
        odom.child_frame_id = child_frame_id;
    
        odom.pose.pose.position.x = easting;
        odom.pose.pose.position.y = northing;
        odom.pose.pose.position.z = fix->altitude;
        
        odom.pose.pose.orientation.x = 0;
        odom.pose.pose.orientation.y = 0;
        odom.pose.pose.orientation.z = 0;
        odom.pose.pose.orientation.w = 1;
        
        // Use ENU covariance to build XYZRPY covariance
        boost::array<double, 36> covariance = {{
          fix->position_covariance[0],
          fix->position_covariance[1],
          fix->position_covariance[2],
          0, 0, 0,
          fix->position_covariance[3],
          fix->position_covariance[4],
          fix->position_covariance[5],
          0, 0, 0,
          fix->position_covariance[6],
          fix->position_covariance[7],
          fix->position_covariance[8],
          0, 0, 0,
          0, 0, 0, rot_cov, 0, 0,
          0, 0, 0, 0, rot_cov, 0,
          0, 0, 0, 0, 0, rot_cov
        }};
    
        odom.pose.covariance = covariance;
    
        odom_pub.publish(odom);
      }
    }
    
    int main (int argc, char **argv) {
      ros::init(argc, argv, "utm_odometry_node");
      ros::NodeHandle node;
      ros::NodeHandle priv_node("~");
    
      priv_node.param<std::string>("frame_id", frame_id, "");
      priv_node.param<std::string>("child_frame_id", child_frame_id, "");
      priv_node.param<double>("rot_covariance", rot_cov, 99999.0);
      priv_node.param<bool>("append_zone", append_zone, false);
    
      odom_pub = node.advertise<nav_msgs::Odometry>("odom", 10);
    
      ros::Subscriber fix_sub = node.subscribe("fix", 10, callback);
    
      ros::spin();
    }
    

    坐标转换函数所在的头文件conversion.h:

    /* Taken from utexas-art-ros-pkg:art_vehicle/applanix */
    
    /*
     * Conversions between coordinate systems.
     *
     * Includes LatLong<->UTM.
     */
    
    #ifndef _UTM_H
    #define _UTM_H
    
    /**  @file
    
         @brief Universal Transverse Mercator transforms.
    
         Functions to convert (spherical) latitude and longitude to and
         from (Euclidean) UTM coordinates.
    
         @author Chuck Gantz- chuck.gantz@globalstar.com
    
     */
    
    #include <cmath>
    #include <cstdio>
    #include <cstdlib>
    
    namespace gps_common
    {
    
    const double RADIANS_PER_DEGREE = M_PI/180.0;
    const double DEGREES_PER_RADIAN = 180.0/M_PI;
    
    // WGS84 Parameters
    const double WGS84_A = 6378137.0;		// major axis
    const double WGS84_B = 6356752.31424518;	// minor axis
    const double WGS84_F = 0.0033528107;		// ellipsoid flattening
    const double WGS84_E = 0.0818191908;		// first eccentricity
    const double WGS84_EP = 0.0820944379;		// second eccentricity
    
    // UTM Parameters
    const double UTM_K0 = 0.9996;			// scale factor
    const double UTM_FE = 500000.0;		// false easting
    const double UTM_FN_N = 0.0;			// false northing on north hemisphere
    const double UTM_FN_S = 10000000.0;		// false northing on south hemisphere
    const double UTM_E2 = (WGS84_E*WGS84_E);	// e^2
    const double UTM_E4 = (UTM_E2*UTM_E2);		// e^4
    const double UTM_E6 = (UTM_E4*UTM_E2);		// e^6
    const double UTM_EP2 = (UTM_E2/(1-UTM_E2));	// e'^2
    
    /**
     * Utility function to convert geodetic to UTM position
     *
     * Units in are floating point degrees (sign for east/west)
     *
     * Units out are meters
     */
    static inline void UTM(double lat, double lon, double *x, double *y)
    {
      // constants
      const static double m0 = (1 - UTM_E2/4 - 3*UTM_E4/64 - 5*UTM_E6/256);
      const static double m1 = -(3*UTM_E2/8 + 3*UTM_E4/32 + 45*UTM_E6/1024);
      const static double m2 = (15*UTM_E4/256 + 45*UTM_E6/1024);
      const static double m3 = -(35*UTM_E6/3072);
    
      // compute the central meridian
      int cm = ((lon >= 0.0)
    	    ? ((int)lon - ((int)lon)%6 + 3)
    	    : ((int)lon - ((int)lon)%6 - 3));
    
      // convert degrees into radians
      double rlat = lat * RADIANS_PER_DEGREE;
      double rlon = lon * RADIANS_PER_DEGREE;
      double rlon0 = cm * RADIANS_PER_DEGREE;
    
      // compute trigonometric functions
      double slat = sin(rlat);
      double clat = cos(rlat);
      double tlat = tan(rlat);
    
      // decide the false northing at origin
      double fn = (lat > 0) ? UTM_FN_N : UTM_FN_S;
    
      double T = tlat * tlat;
      double C = UTM_EP2 * clat * clat;
      double A = (rlon - rlon0) * clat;
      double M = WGS84_A * (m0*rlat + m1*sin(2*rlat)
    			+ m2*sin(4*rlat) + m3*sin(6*rlat));
      double V = WGS84_A / sqrt(1 - UTM_E2*slat*slat);
    
      // compute the easting-northing coordinates
      *x = UTM_FE + UTM_K0 * V * (A + (1-T+C)*pow(A,3)/6
    			      + (5-18*T+T*T+72*C-58*UTM_EP2)*pow(A,5)/120);
      *y = fn + UTM_K0 * (M + V * tlat * (A*A/2
    				      + (5-T+9*C+4*C*C)*pow(A,4)/24
    				      + ((61-58*T+T*T+600*C-330*UTM_EP2)
    					 * pow(A,6)/720)));
    
      return;
    }
    
    /**
     * Determine the correct UTM letter designator for the
     * given latitude
     *
     * @returns 'Z' if latitude is outside the UTM limits of 84N to 80S
     *
     * Written by Chuck Gantz- chuck.gantz@globalstar.com
     */
    static inline char UTMLetterDesignator(double Lat)
    {
    	char LetterDesignator;
    
    	if     ((84 >= Lat) && (Lat >= 72))  LetterDesignator = 'X';
    	else if ((72 > Lat) && (Lat >= 64))  LetterDesignator = 'W';
    	else if ((64 > Lat) && (Lat >= 56))  LetterDesignator = 'V';
    	else if ((56 > Lat) && (Lat >= 48))  LetterDesignator = 'U';
    	else if ((48 > Lat) && (Lat >= 40))  LetterDesignator = 'T';
    	else if ((40 > Lat) && (Lat >= 32))  LetterDesignator = 'S';
    	else if ((32 > Lat) && (Lat >= 24))  LetterDesignator = 'R';
    	else if ((24 > Lat) && (Lat >= 16))  LetterDesignator = 'Q';
    	else if ((16 > Lat) && (Lat >= 8))   LetterDesignator = 'P';
    	else if (( 8 > Lat) && (Lat >= 0))   LetterDesignator = 'N';
    	else if (( 0 > Lat) && (Lat >= -8))  LetterDesignator = 'M';
    	else if ((-8 > Lat) && (Lat >= -16)) LetterDesignator = 'L';
    	else if((-16 > Lat) && (Lat >= -24)) LetterDesignator = 'K';
    	else if((-24 > Lat) && (Lat >= -32)) LetterDesignator = 'J';
    	else if((-32 > Lat) && (Lat >= -40)) LetterDesignator = 'H';
    	else if((-40 > Lat) && (Lat >= -48)) LetterDesignator = 'G';
    	else if((-48 > Lat) && (Lat >= -56)) LetterDesignator = 'F';
    	else if((-56 > Lat) && (Lat >= -64)) LetterDesignator = 'E';
    	else if((-64 > Lat) && (Lat >= -72)) LetterDesignator = 'D';
    	else if((-72 > Lat) && (Lat >= -80)) LetterDesignator = 'C';
            // 'Z' is an error flag, the Latitude is outside the UTM limits
    	else LetterDesignator = 'Z';
    	return LetterDesignator;
    }
    
    /**
     * Convert lat/long to UTM coords.  Equations from USGS Bulletin 1532
     *
     * East Longitudes are positive, West longitudes are negative.
     * North latitudes are positive, South latitudes are negative
     * Lat and Long are in fractional degrees
     *
     * Written by Chuck Gantz- chuck.gantz@globalstar.com
     */
    static inline void LLtoUTM(const double Lat, const double Long,
                               double &UTMNorthing, double &UTMEasting,
                               char* UTMZone)
    {
    	double a = WGS84_A;
    	double eccSquared = UTM_E2;
    	double k0 = UTM_K0;
    
    	double LongOrigin;
    	double eccPrimeSquared;
    	double N, T, C, A, M;
    
            //Make sure the longitude is between -180.00 .. 179.9
    	double LongTemp = (Long+180)-int((Long+180)/360)*360-180;
    
    	double LatRad = Lat*RADIANS_PER_DEGREE;
    	double LongRad = LongTemp*RADIANS_PER_DEGREE;
    	double LongOriginRad;
    	int    ZoneNumber;
    
    	ZoneNumber = int((LongTemp + 180)/6) + 1;
    
    	if( Lat >= 56.0 && Lat < 64.0 && LongTemp >= 3.0 && LongTemp < 12.0 )
    		ZoneNumber = 32;
    
            // Special zones for Svalbard
    	if( Lat >= 72.0 && Lat < 84.0 )
    	{
    	  if(      LongTemp >= 0.0  && LongTemp <  9.0 ) ZoneNumber = 31;
    	  else if( LongTemp >= 9.0  && LongTemp < 21.0 ) ZoneNumber = 33;
    	  else if( LongTemp >= 21.0 && LongTemp < 33.0 ) ZoneNumber = 35;
    	  else if( LongTemp >= 33.0 && LongTemp < 42.0 ) ZoneNumber = 37;
    	 }
            // +3 puts origin in middle of zone
    	LongOrigin = (ZoneNumber - 1)*6 - 180 + 3;
    	LongOriginRad = LongOrigin * RADIANS_PER_DEGREE;
    
    	//compute the UTM Zone from the latitude and longitude
    	snprintf(UTMZone, 4, "%d%c", ZoneNumber, UTMLetterDesignator(Lat));
    
    	eccPrimeSquared = (eccSquared)/(1-eccSquared);
    
    	N = a/sqrt(1-eccSquared*sin(LatRad)*sin(LatRad));
    	T = tan(LatRad)*tan(LatRad);
    	C = eccPrimeSquared*cos(LatRad)*cos(LatRad);
    	A = cos(LatRad)*(LongRad-LongOriginRad);
    
    	M = a*((1	- eccSquared/4		- 3*eccSquared*eccSquared/64	- 5*eccSquared*eccSquared*eccSquared/256)*LatRad
    				- (3*eccSquared/8	+ 3*eccSquared*eccSquared/32	+ 45*eccSquared*eccSquared*eccSquared/1024)*sin(2*LatRad)
    									+ (15*eccSquared*eccSquared/256 + 45*eccSquared*eccSquared*eccSquared/1024)*sin(4*LatRad)
    									- (35*eccSquared*eccSquared*eccSquared/3072)*sin(6*LatRad));
    
    	UTMEasting = (double)(k0*N*(A+(1-T+C)*A*A*A/6
    					+ (5-18*T+T*T+72*C-58*eccPrimeSquared)*A*A*A*A*A/120)
    					+ 500000.0);
    
    	UTMNorthing = (double)(k0*(M+N*tan(LatRad)*(A*A/2+(5-T+9*C+4*C*C)*A*A*A*A/24
    				 + (61-58*T+T*T+600*C-330*eccPrimeSquared)*A*A*A*A*A*A/720)));
    	if(Lat < 0)
    		UTMNorthing += 10000000.0; //10000000 meter offset for southern hemisphere
    }
    
    static inline void LLtoUTM(const double Lat, const double Long,
                               double &UTMNorthing, double &UTMEasting,
                               std::string &UTMZone) {
      char zone_buf[] = {0, 0, 0, 0};
    
      LLtoUTM(Lat, Long, UTMNorthing, UTMEasting, zone_buf);
    
      UTMZone = zone_buf;
    }
    
    /**
     * Converts UTM coords to lat/long.  Equations from USGS Bulletin 1532
     *
     * East Longitudes are positive, West longitudes are negative.
     * North latitudes are positive, South latitudes are negative
     * Lat and Long are in fractional degrees.
     *
     * Written by Chuck Gantz- chuck.gantz@globalstar.com
     */
    static inline void UTMtoLL(const double UTMNorthing, const double UTMEasting,
                               const char* UTMZone, double& Lat,  double& Long )
    {
    	double k0 = UTM_K0;
    	double a = WGS84_A;
    	double eccSquared = UTM_E2;
    	double eccPrimeSquared;
    	double e1 = (1-sqrt(1-eccSquared))/(1+sqrt(1-eccSquared));
    	double N1, T1, C1, R1, D, M;
    	double LongOrigin;
    	double mu, phi1Rad;
    	double x, y;
    	int ZoneNumber;
    	char* ZoneLetter;
    
    	x = UTMEasting - 500000.0; //remove 500,000 meter offset for longitude
    	y = UTMNorthing;
    
    	ZoneNumber = strtoul(UTMZone, &ZoneLetter, 10);
    	if((*ZoneLetter - 'N') < 0)
    	{
    		y -= 10000000.0;//remove 10,000,000 meter offset used for southern hemisphere
    	}
    
    	LongOrigin = (ZoneNumber - 1)*6 - 180 + 3;  //+3 puts origin in middle of zone
    
    	eccPrimeSquared = (eccSquared)/(1-eccSquared);
    
    	M = y / k0;
    	mu = M/(a*(1-eccSquared/4-3*eccSquared*eccSquared/64-5*eccSquared*eccSquared*eccSquared/256));
    
    	phi1Rad = mu	+ (3*e1/2-27*e1*e1*e1/32)*sin(2*mu)
    				+ (21*e1*e1/16-55*e1*e1*e1*e1/32)*sin(4*mu)
    				+(151*e1*e1*e1/96)*sin(6*mu);
    
    	N1 = a/sqrt(1-eccSquared*sin(phi1Rad)*sin(phi1Rad));
    	T1 = tan(phi1Rad)*tan(phi1Rad);
    	C1 = eccPrimeSquared*cos(phi1Rad)*cos(phi1Rad);
    	R1 = a*(1-eccSquared)/pow(1-eccSquared*sin(phi1Rad)*sin(phi1Rad), 1.5);
    	D = x/(N1*k0);
    
    	Lat = phi1Rad - (N1*tan(phi1Rad)/R1)*(D*D/2-(5+3*T1+10*C1-4*C1*C1-9*eccPrimeSquared)*D*D*D*D/24
    					+(61+90*T1+298*C1+45*T1*T1-252*eccPrimeSquared-3*C1*C1)*D*D*D*D*D*D/720);
    	Lat = Lat * DEGREES_PER_RADIAN;
    
    	Long = (D-(1+2*T1+C1)*D*D*D/6+(5-2*C1+28*T1-3*C1*C1+8*eccPrimeSquared+24*T1*T1)
    					*D*D*D*D*D/120)/cos(phi1Rad);
    	Long = LongOrigin + Long * DEGREES_PER_RADIAN;
    
    }
    
    static inline void UTMtoLL(const double UTMNorthing, const double UTMEasting,
        std::string UTMZone, double& Lat, double& Long) {
      UTMtoLL(UTMNorthing, UTMEasting, UTMZone.c_str(), Lat, Long);
    }
    } // end namespace UTM
    
    #endif // _UTM_H
    

    运行:

    rosrun gps_common utm_odometry_node
    

    或者,创建launch文件utm_odometry_node.launch

    <launch>
    <node name="gps_conv" pkg="gps_common" type="utm_odometry_node">
      <remap from="odom" to="vo"/>
      <remap from="fix" to="/gps/fix" />
      <param name="rot_covariance" value="99999" />
      <param name="frame_id" value="base_footprint" />
    </node>
    </launch>
    

    注意:参数根据自己的需求自定义。

    然后运行:

    roslaunch gps_common utm_odometry_node.launch
    

    3.2 UTM坐标转换为GPS坐标

    代码在~/gps_ws/src/gps_umd/gps_common/src/utm_odometry_to_navsatfix_node.cpp,这里就不贴了。

    注:代码写得标准又易读,值得学习,这也是我在这里贴代码的原因。

    4 sensor_msgs/NavSatFix与gps_common/GPSFix的转换

    sensor_msgs/NavSatFix的内容见:http://docs.ros.org/api/sensor_msgs/html/msg/NavSatFix.html

    gps_common/GPSFix的路径为~/tingjiandan/gps_ws/src/gps_umd/gps_common/msg/GPSFix.msg,描述如下:

    # A more complete GPS fix to supplement sensor_msgs/NavSatFix.

    主函数fix_translator.py:

    #!/usr/bin/env python
    
    # Translates from NavSatFix to GPSFix and back
    
    import rospy
    from sensor_msgs.msg import NavSatFix
    from gps_common.msg import GPSFix
    import gps_common.gps_message_converter as converter
    
    navsat_pub = rospy.Publisher('navsat_fix_out', NavSatFix, queue_size=10)
    gps_pub = rospy.Publisher('gps_fix_out', GPSFix, queue_size=10)
    
    def navsat_callback(navsat_msg):
        gps_msg = converter.navsatfix_to_gpsfix(navsat_msg)
        gps_pub.publish(gps_msg)
    
    # Translates from GPSFix to NavSatFix.
    # As GPSFix can store much more information than NavSatFix, 
    # a lot of this additional information might get lost.
    def gps_callback(gps_msg):
        navsat_msg = converter.gpsfix_to_navsatfix(gps_msg)
        navsat_pub.publish(navsat_msg)
    
    if __name__ == '__main__':
        rospy.init_node('fix_translator', anonymous=True)
        navsat_sub = rospy.Subscriber("navsat_fix_in", NavSatFix, navsat_callback)
        gps_sub = rospy.Subscriber("gps_fix_in", GPSFix, gps_callback)
        rospy.spin()
    

    消息转换函数gps_message_converter.py:

    from sensor_msgs.msg import NavSatFix
    from sensor_msgs.msg import NavSatStatus
    from gps_common.msg import GPSFix
    from gps_common.msg import GPSStatus
    
    def navsatfix_to_gpsfix(navsat_msg):
        # Convert sensor_msgs/NavSatFix messages to gps_common/GPSFix messages
        gpsfix_msg = GPSFix()
        gpsfix_msg.header = navsat_msg.header
        gpsfix_msg.status.status = navsat_msg.status.status
    
        gpsfix_msg.status.motion_source = GPSStatus.SOURCE_NONE
        gpsfix_msg.status.orientation_source = GPSStatus.SOURCE_NONE
        gpsfix_msg.status.position_source = GPSStatus.SOURCE_NONE
        if ((navsat_msg.status.service & NavSatStatus.SERVICE_GPS) or
                (navsat_msg.status.service & NavSatStatus.SERVICE_GLONASS) or
                (navsat_msg.status.service & NavSatStatus.SERVICE_GALILEO)):
            gpsfix_msg.status.motion_source = \
                gpsfix_msg.status.motion_source | GPSStatus.SOURCE_GPS
            gpsfix_msg.status.orientation_source = \
                gpsfix_msg.status.orientation_source | GPSStatus.SOURCE_GPS
            gpsfix_msg.status.position_source = \
                gpsfix_msg.status.position_source | GPSStatus.SOURCE_GPS
    
        if navsat_msg.status.service & NavSatStatus.SERVICE_COMPASS:
            gpsfix_msg.status.orientation_source = \
                gpsfix_msg.status.orientation_source | GPSStatus.SOURCE_MAGNETIC
    
        gpsfix_msg.latitude = navsat_msg.latitude
        gpsfix_msg.longitude = navsat_msg.longitude
        gpsfix_msg.altitude = navsat_msg.altitude
        gpsfix_msg.position_covariance = navsat_msg.position_covariance
        gpsfix_msg.position_covariance_type = navsat_msg.position_covariance_type
    
        return gpsfix_msg
    
    def gpsfix_to_navsatfix(gpsfix_msg):
        # Convert gps_common/GPSFix messages to sensor_msgs/NavSatFix messages
        navsat_msg = NavSatFix()
        navsat_msg.header = gpsfix_msg.header
    
        # Caution: GPSFix has defined some additional status constants, which are
        # not defined in NavSatFix.
        navsat_msg.status.status = gpsfix_msg.status.status
    
        navsat_msg.status.service = 0
        if gpsfix_msg.status.position_source & GPSStatus.SOURCE_GPS:
            navsat_msg.status.service = \
                navsat_msg.status.service | NavSatStatus.SERVICE_GPS
        if gpsfix_msg.status.orientation_source & GPSStatus.SOURCE_MAGNETIC:
            navsat_msg.status.service = \
                navsat_msg.status.service | NavSatStatus.SERVICE_COMPASS
    
        navsat_msg.latitude = gpsfix_msg.latitude
        navsat_msg.longitude = gpsfix_msg.longitude
        navsat_msg.altitude = gpsfix_msg.altitude
        navsat_msg.position_covariance = gpsfix_msg.position_covariance
        navsat_msg.position_covariance_type = gpsfix_msg.position_covariance_type
    
        return navsat_msg
    

    launch文件fix_translator.launch:

    <launch>
    
    <!--
        fix_translator translates to and from NatSatFix 
        and GPSFix messages.
    
        If you want to translate from NavSatFix to GPSFix,
        you have to modify the first two remap lines.
       
        If you want to translate from GPSFix to NavSatFix,
        you have to uncomment and modify the last two remap 
        lines.
    
        Only adjust topic names after "to=" in each remap line.
    -->
    
      <node name="fix_translator" pkg="gps_common" type="fix_translator">
        <!-- Translate from NavSatFix to GPSFix //-->
          <remap from="/navsat_fix_in"  to="/fix"/>       
          <remap from="/gps_fix_out"    to="/gps_fix"/>
    
        <!-- Translate from GPSFix to NavSatFix //-->
         <!--
           <remap from="/gps_fix_in"     to="/YOUR_GPSFIX_TOPIC"/>   
           <remap from="/navsat_fix_out" to="/YOUR_NAVSATFIX_TOPIC"/>   
         //-->
      </node>
    
    </launch>
    

    注释写得很详细,就不翻译了。

    运行:

    roslaunch gps_common fix_translator.launch
    

    注:ROS支持Python,这个项目同时使用了C++和Python,值得学习一下哦。

    5 参考

    [1] Github: http://wiki.ros.org/gps_common
    [2] ROS wiki: http://wiki.ros.org/gps_common

    展开全文
  • UTM坐标转大地坐标

    2012-12-22 17:04:38
    UTM坐标转大地坐标算法研究,供大家参考!
  • 将wgs84格式的坐标写入到txt当中,读取之后自动计算代号,并将转换后的UTM坐标写入到txt中
  • UTM坐标和WGS84坐标转换

    千次阅读 2020-06-18 18:31:42
    UTM坐标简介 像橘子一样均匀地切成60个称为“区域”的部分,展平这些区域中的每个区域,通用横轴Mercator(UTM)投影; 可以这样看:UTM区域是地球的6°区域,因为圆具有360°,这意味着地球上有60个UTM区域。 比如...

    UTM坐标简介
    像橘子一样均匀地切成60个称为“区域”的部分,展平这些区域中的每个区域,通用横轴Mercator(UTM)投影;
    可以这样看:UTM区域是地球的6°区域,因为圆具有360°,这意味着地球上有60个UTM区域。
    在这里插入图片描述
    比如:中国东部地区属于UTM Zone 50N,可以到官网找到目标地区的编号
    官网:http://www.dmap.co.uk/utmworld.htm
    在这里插入图片描述
    原理图:
    X轴:指向东边、Y轴:指向北边、Z轴:指向天顶

    展开全文
  • UTM(Universal Transverse Mercator)坐标是一个投影坐标系,将地球分为60个区,单位为m。 二者的转换可以利用商业软件,如Global Mapper等。下面给出了经纬度转UTM的matlab程序。 转换公式:(只针对北半球,...
  • novatel计算odom--GPS坐标与UTM坐标转换

    千次阅读 2020-03-31 17:24:58
    保证你的novatel的driver是在ros-drivers上的驱动 1 简介 1.1 消息 gps_common定义了两个通用消息,供GPS驱动程序输出:gps_common/GPSFix和gps_common/GPSStatus。...utm_odometry_node将经...
  • UTM坐标和WGS84坐标(如何转换?)

    万次阅读 2020-02-27 20:46:15
    一、UTM坐标简介 二、WGS84简介 三、WGS84 转 UTM 四、UTM如何转换为WGS84坐标
  • 该程序使用 Coticchia-Surace 公式*将地理坐标(十进制格式的经度和纬度)转换UTM 坐标(以米为单位)。 可以使用 22 种不同的椭球,当然包括 WGS84。 界面非常简单。 可以转换单个点或点列表。 II.- 它是...
  • 用于地理坐标转换UTM与WGS84坐标系互转互相转化的C/C++代码实现。
  • 如题所说,直接上程序。...%地理经纬度坐标转换UTM坐标 size_shuzu=size(lat_shuru); for i=1:size_shuzu(2) %输入经纬度 % lat=29.819206; % lon=116.133243; lat=lat_shuru(i); lon=lon_shuru(i); %%
  • 进行坐标转换(实现) 初始化坐标参考系统 构建转换对象 转换坐标 获取gps坐标 随意选取一个gps坐标为:北纬30°43'31.757",东经120°30'18.910" 根据中国utm分区表,确定所在地区的utm分区 根据drsu的...
  • UTM大地坐标系与经纬度转换算法C++

    千次阅读 2021-05-24 19:54:47
    UTM坐标系,需要确定给定UTM区域的中央子午线。 分为三分度和六分度。 三分度 3度带:中央子午线计算公式:中央子午线L=3 ×N 。N=当地经度/3,N值进行四舍五入后即为3度带的带号。 六分度 6度带:中央子午线计算...
  • c# WGS84坐标转换UTM坐标

    千次阅读 2019-07-03 16:51:11
    通过查阅相关资料,有一篇博客里面给出了WGS84坐标转换UTM坐标的功能,该博主使用matlab程序实现坐标的转换,基于已有的公式,用c#语言实现坐标的转换。 参考的博客连接如下: ... c#实现坐标转换的代码如下: ...
  • UTM2LL将通用横向墨卡托(UTM)的东/北坐标转换为纬度/经度。 LL2UTM 将纬度/经度坐标转换UTM。 这两个函数都使用精确公式(毫米精度)、可能的用户定义数据(WGS84 是默认值),并且都是矢量化的(代码中没有...

空空如也

空空如也

1 2 3 4 5 ... 20
收藏数 2,960
精华内容 1,184
关键字:

utm坐标转换