一、各大坐標系
目前地圖開發離不開定位,定位又離不開坐標系的選取和轉換,所以有必要簡單說一下啦。
世界大地坐標(WGS84)
1.國際上采用的標准,是為GPS全球定位系統使用而建立的坐標系統,可從專業GPS設備中獲取數據。
2.國際地圖使用的坐標系。
3.谷歌國外地圖、osm地圖
火星坐標(GCJ-02)
1.中國采用的標准,准確是叫國測局坐標系,可從國行移動設備定位獲得數據
2.國內出版的各類地圖都至少采用GCJ-02對地理位置進行加密偏移
3.高德地圖、天地圖、搜搜地圖等
百度坐標(BD-09)
1.百度地圖自己采用的坐標標准。
2.百度坐標是在GCJ-02的基礎上再次加密
3.百度地圖
二、各大坐標系間的轉換
通用實體
1 /// <summary> 2 /// 經度和緯度 3 /// </summary> 4 public class StationGps 5 { 6 /// <summary> 7 /// 經度 8 /// </summary> 9 public double longitude { get; set; } 10 /// <summary> 11 /// 緯度 12 /// </summary> 13 public double latitude { get; set; } 14 }
1、火星坐標轉百度

1 private static double x_pi = 3.14159265358979324 * 3000.0 / 180.0; 2 3 public static StationGps HxToBd(double lon, double lat) 4 { 5 var result = new StationGps(); 6 double x = lon, y = lat; 7 var z = Math.Sqrt(x * x + y * y) + 0.00002 * Math.Sin(y * x_pi); 8 var theta = Math.Atan2(y, x) + 0.000003 * Math.Cos(x * x_pi); 9 result.longitude = z * Math.Cos(theta) + 0.0065; 10 result.latitude = z * Math.Sin(theta) + 0.006; 11 return result; 12 }
2、百度轉火星坐標

1 private static double x_pi = 3.14159265358979324 * 3000.0 / 180.0; 2 3 public static StationGps BdToHx(double lon, double lat) 4 { 5 var result = new StationGps(); 6 double x = lon - 0.0065, y = lat - 0.006; 7 var z = Math.Sqrt(x * x + y * y) - 0.00002 * Math.Sin(y * x_pi); 8 var theta = Math.Atan2(y, x) - 0.000003 * Math.Cos(x * x_pi); 9 result.longitude = z * Math.Cos(theta); 10 result.latitude = z * Math.Sin(theta); 11 return result; 12 }
3、世界大地坐標轉火星坐標

1 private static double pi = 3.14159265358979324; 2 private static double a = 6378245.0; 3 private static double ee = 0.00669342162296594323; 4 5 public static StationGps WgsToHx(double lon, double lat) 6 { 7 var result = new StationGps(); 8 double dLat = TransformLat(lat - 35.0, lon - 105.0); 9 double dLon = TransformLon(lat - 35.0, lon - 105.0); 10 double radLat = lat / 180.0 * pi; 11 double magic = Math.Sin(radLat); 12 magic = 1 - ee * magic * magic; 13 var sqrtMagic = Math.Sqrt(magic); 14 dLat = (dLat * 180.0) / ((a * (1 - ee)) / (magic * sqrtMagic) * pi); 15 dLon = (dLon * 180.0) / (a / sqrtMagic * Math.Cos(radLat) * pi); 16 result.latitude = lat + dLat; 17 result.longitude = lon + dLon; 18 return result; 19 } 20 21 private static double TransformLat(double lon, double lat) 22 { 23 var ret = -100.0 + 2.0 * lat + 3.0 * lon + 0.2 * lon * lon + 0.1 * lat * lon + 0.2 * Math.Sqrt(Math.Abs(lat)); 24 ret += (20.0 * Math.Sin(6.0 * lat * pi) + 20.0 * Math.Sin(2.0 * lat * pi)) * 2.0 / 3.0; 25 ret += (20.0 * Math.Sin(lon * pi) + 40.0 * Math.Sin(lon / 3.0 * pi)) * 2.0 / 3.0; 26 ret += (160.0 * Math.Sin(lon / 12.0 * pi) + 320 * Math.Sin(lon * pi / 30.0)) * 2.0 / 3.0; 27 return ret; 28 } 29 private static double TransformLon(double lon, double lat) 30 { 31 var ret = 300.0 + lat + 2.0 * lon + 0.1 * lat * lat + 0.1 * lat * lon + 0.1 * Math.Sqrt(Math.Abs(lat)); 32 ret += (20.0 * Math.Sin(6.0 * lat * pi) + 20.0 * Math.Sin(2.0 * lat * pi)) * 2.0 / 3.0; 33 ret += (20.0 * Math.Sin(lat * pi) + 40.0 * Math.Sin(lat / 3.0 * pi)) * 2.0 / 3.0; 34 ret += (150.0 * Math.Sin(lat / 12.0 * pi) + 300.0 * Math.Sin(lat / 30.0 * pi)) * 2.0 / 3.0; 35 return ret; 36 }
4、世界大地坐標轉為百度坐標

1 private static double pi = 3.14159265358979324; 2 private static double a = 6378245.0; 3 private static double ee = 0.00669342162296594323; 4 private static double x_pi = 3.14159265358979324 * 3000.0 / 180.0; 5 6 public static StationGps WgsToBd(double lon, double lat) 7 { 8 var hx = WgsToHx(lon, lat); 9 var bd = HxToBd(hx.longitude, hx.latitude); 10 return bd; 11 } 12 13 public static StationGps HxToBd(double lon, double lat) 14 { 15 var result = new StationGps(); 16 double x = lon, y = lat; 17 var z = Math.Sqrt(x * x + y * y) + 0.00002 * Math.Sin(y * x_pi); 18 var theta = Math.Atan2(y, x) + 0.000003 * Math.Cos(x * x_pi); 19 result.longitude = z * Math.Cos(theta) + 0.0065; 20 result.latitude = z * Math.Sin(theta) + 0.006; 21 return result; 22 } 23 24 public static StationGps WgsToHx(double lon, double lat) 25 { 26 var result = new StationGps(); 27 double dLat = TransformLat(lat - 35.0, lon - 105.0); 28 double dLon = TransformLon(lat - 35.0, lon - 105.0); 29 double radLat = lat / 180.0 * pi; 30 double magic = Math.Sin(radLat); 31 magic = 1 - ee * magic * magic; 32 var sqrtMagic = Math.Sqrt(magic); 33 dLat = (dLat * 180.0) / ((a * (1 - ee)) / (magic * sqrtMagic) * pi); 34 dLon = (dLon * 180.0) / (a / sqrtMagic * Math.Cos(radLat) * pi); 35 result.latitude = lat + dLat; 36 result.longitude = lon + dLon; 37 return result; 38 } 39 40 private static double TransformLat(double lon, double lat) 41 { 42 var ret = -100.0 + 2.0 * lat + 3.0 * lon + 0.2 * lon * lon + 0.1 * lat * lon + 0.2 * Math.Sqrt(Math.Abs(lat)); 43 ret += (20.0 * Math.Sin(6.0 * lat * pi) + 20.0 * Math.Sin(2.0 * lat * pi)) * 2.0 / 3.0; 44 ret += (20.0 * Math.Sin(lon * pi) + 40.0 * Math.Sin(lon / 3.0 * pi)) * 2.0 / 3.0; 45 ret += (160.0 * Math.Sin(lon / 12.0 * pi) + 320 * Math.Sin(lon * pi / 30.0)) * 2.0 / 3.0; 46 return ret; 47 } 48 49 private static double TransformLon(double lon, double lat) 50 { 51 var ret = 300.0 + lat + 2.0 * lon + 0.1 * lat * lat + 0.1 * lat * lon + 0.1 * Math.Sqrt(Math.Abs(lat)); 52 ret += (20.0 * Math.Sin(6.0 * lat * pi) + 20.0 * Math.Sin(2.0 * lat * pi)) * 2.0 / 3.0; 53 ret += (20.0 * Math.Sin(lat * pi) + 40.0 * Math.Sin(lat / 3.0 * pi)) * 2.0 / 3.0; 54 ret += (150.0 * Math.Sin(lat / 12.0 * pi) + 300.0 * Math.Sin(lat / 30.0 * pi)) * 2.0 / 3.0; 55 return ret; 56 }