http://bbs.amap.com/thread-18617-1-1.html#rd?sukey=cbbc36a2500a2e6c2b0b19115118ace519002ff3a52731f1388ddf5bf3a144e9ae715c2253b0bba87b05dcc82d6c0e74javascript
摘要:各类坐标体系之间如何转换?到底有哪些坐标体系?什么是火星坐标?为何个人坐标,在地图上显示会有偏移?本文详细解答以上问题。最后给出坐标拾取工具。
---------------------------------------------------------------------------------------------------------------------------
1、坐标体系
首先咱们要明白,开发者能接触到哪些坐标体系呢?
第一种分类:
一、 GPS,WGS-84,原始坐标体系。通常用国际标准的GPS记录仪记录下来的坐标,都是GPS的坐标。很惋惜,在中国,任何一个地图产品都不容许使用GPS坐标,听说是为了保密。GPS坐标形式如图,度分秒形式的经纬度:
二、 GCJ-02,国测局02年发布的坐标体系。又称“火星坐标”。在中国,必须至少使用GCJ-02的坐标体系。好比谷歌,腾讯,高德都在用这个坐标体系。GCJ-02也是国内最普遍使用的坐标体系。
三、 其余坐标体系。通常都是由GCJ-02进过偏移算法获得的。这种体系就根据每一个公司的不一样,坐标体系都不同了。好比,百度和搜狗就使用本身的坐标体系,与其余坐标体系不兼容。
第二种分类:
首先明白,全部坐标体系的原点,都是非洲。
一、 经纬度。这个是球面坐标,对于北京来讲,就是(116.38817139.935961)这样的坐标。好比腾讯、高德、百度都是这样的经纬度坐标。谷歌是经纬度顺序写反的经纬度坐标。
若是是度分秒坐标,须要进行转换,才能获得这样的经纬度坐标。详见坐标转换。
二、 墨卡托坐标。平面坐标,至关因而直线距离,数字通常都比较大,像这样的。(215362.00021333335 99526.00034912192)
墨卡托坐标,主要用于程序的后台计算。直线距离嘛,加加减减几乎计算方便。
搜狗地图API就是直接使用的墨卡托坐标。
2、坐标转换
在各类web端平台,或者高德、腾讯、百度上取到的坐标,都不是GPS坐标,都是GCJ-02坐标,或者本身的偏移坐标系。
好比,你在谷歌地图API,高德地图API,腾讯地图API上取到的,都是GCJ-02坐标,他们三家都是通用的,也适用于大部分地图API产品,以及他们的地图产品。
例外,百度API上取到的,是BD-09坐标,只适用于百度地图相关产品。
例外,搜狗API上取到的,是搜狗坐标,只适用于搜狗地图相关产品。
例外,谷歌地球,google earth上取到的,是GPS坐标,并且是度分秒形式的经纬度坐标。在国内不容许使用。必须转换为GCJ-02坐标。
一、度分秒坐标转换为经纬度
好比,在GPS记录仪,或者google earth上采集到的是39°31'20.51,那么应该这样换算,31分就是31/60度,20.51秒就是20.51/3600度,结果就是39 + 31/60 + 20.51/3600 度。
二、 GPS转换为GCJ-02坐标
谷歌,高德,腾讯的地图API官网上,都不直接提供这样的坐标转换。若是要获得GCJ-02坐标,最好在他们的地图上直接取点,或者经过地址解析获得。(这个工具我后续会贴出来的。我就爱干这样的事情,哈哈。)
不过,在网上搜到了这样的接口,该接口的type=1就是GPS转到GCJ-02的墨卡托坐标。请你们对接口保密,哈哈。详见:
http://map.sogou.com/api/documentation/javascript/api2.5/interface_translate.html#late_intro
三、GCJ-02与BD-09之间互转
国测局GCJ-02坐标体系(谷歌、高德、腾讯),与百度坐标BD-09体系的转换,在CSDN上有很详细的讲解:
http://blog.csdn.net/coolypf/article/details/8569813
不过也有更简单的算法,线性算法(lat和lng是经纬度,球面坐标):
To_B是转到百度,To_G是转到GCJ-02。
var TO_BLNG = function(lng){return lng+0.0065;};
var TO_BLAT = function(lat){return lat+0.0060;};
var TO_GLNG = function(lng){return lng-0.0065;};
var TO_GLAT = function(lat){return lat-0.0060;};
四、经纬纬度转成墨卡托
网上也有详细讲解:
http://bbs.esrichina-bj.cn/esri/viewthread.php?tid=78245
五、各家API公司坐标转换接口的申请
通常须要将您的公司名称、项目名称、项目简介、联系人和联系方式,发邮件至地图API公司的商务部,通过申请,才能使用。
下面是他们的联系方式:
高德地图
|
|
百度地图
|
|
腾讯地图
|
|
谷歌地图
|
这个,国内没有公交接口,你们应该不会再使用了吧。
|
(你们发现没,高德是api,腾讯和百度是mapapi,说明什么?)
3、坐标偏移
若是您的坐标在转换以后,还有偏移,那么考虑如下几个方面。
A、原始坐标系弄错,好比觉得本身是GPS坐标,但其实已是GCJ-02坐标。
解决方案:请确保采集到的数据是哪一个坐标体系,须要转换到哪一个坐标系,再进行坐标转换。
B、原始坐标准确度不够
解决方案:若是您是GPS坐标,请确保采集GPS数据时,搜到至少4颗以上的卫星。而且GPS数据准不许,还取决于周围建筑物的高度,越高越不许,由于有遮挡。
若是原本就是GCJ-02坐标,在不一样地图放大级别的时候,看到的地方可能不同。好比你在地图级别4(国家)取到的坐标,放大到地图12级(街道)时,坐标就偏了。请确保在地图最大放大级别时,拾取坐标。
C、度分秒的概念混淆
好比,在google earth上采集到的是39°31'20.51,那么应该这样换算,31分就是31/60度,20.51秒就是20.51/3600度,结果就是39 + 31/60 + 20.51/3600 度。
D、经纬度顺序写反了
有些公司(好比高德,百度,腾讯)是先经度,再纬度,即Point(lng lat)。但谷歌坐标的顺序刚好相反,是(lat lng)。
4、坐标拾取工具
既然在国内必须至少使用GCJ-02的坐标系,而GCJ-02,“火星坐标”是在国内最普遍使用的坐标体系。那么,咱们就来看看,如何直接获取到GCJ-02坐标呗。
请你们把这段代码保存到记事本里,而后后缀名改成.html,记得用UTF-8编码来保存。而后双击这个文件,就能打开网页了。
<!
DOCTYPE HTML
>
<
html
>
<
head
>
<
meta
http-equiv
="Content-Type"
content
="text/html; charset=utf-8"
>
<
title
>火星坐标拾取
</
title
>
<
script
language
="javascript"
src
="http://webapi.amap.com/maps?v=1.2&key=6260f3e133c146a76f7c210c2786aec9"
></
script
>
<
style
>
#iMap
{
height
:
500px
;
width
:
600px
;
float
:
left
;
}
.info
{
float
:
left
;
margin
:
0 0 0 10px
;
}
label
{
width
:
80px
;
float
:
left
;
}
</
style
>
</
head
>
<
body
onLoad
="mapInit()"
>
<
div
id
="iMap"
></
div
>
<
div
class
="info"
>
<
p
><
label
>火星坐标:
</
label
><
span
id
="lnglat"
>
</
span
></
p
>
<
p
><
label
>地址:
</
label
><
span
id
="iAddress"
>
</
span
></
p
>
</
br
>
<
p
>说明:
</
p
>
<
p
>一、鼠标滚轮能够缩放地图,拖动地图。
</
p
>
<
p
>二、点击地图,便可得到GCJ-02的经纬度坐标,地址。
</
p
>
</
div
>
</
body
>
<
script
language
="javascript"
>
var
mapObj;
var
lnglatXY;
//
初始化地图
function
mapInit(){
var
opt
=
{ level:
13
//
设置地图缩放级别
center:
new
AMap.LngLat(
116.397428
39.90923
)
//
设置地图中心点
} mapObj
=
new
AMap.Map(
"
iMap
"
opt); AMap.event.addListener(mapObj
'
click
'
getLnglat);
//
点击事件
}
function
geocoder() {
var
MGeocoder;
//
加载地理编码插件
mapObj.plugin([
"
AMap.Geocoder
"
]
function
() { MGeocoder
=
new
AMap.Geocoder({ radius:
1000
extensions:
"
all
"
});
//
返回地理编码结果
AMap.event.addListener(MGeocoder
"
complete
"
geocoder_CallBack);
//
逆地理编码
MGeocoder.getAddress(lnglatXY); });
//
加点
var
marker
=
new
AMap.Marker({ map:mapObj icon:
new
AMap.Icon({ image:
"
http://api.amap.com/Public/images/js/mark.png
"
size:
new
AMap.Size(
58
30
) imageOffset:
new
AMap.Pixel(
-
32
-
0
) }) position: lnglatXY offset:
new
AMap.Pixel(
-
5
-
30
) }); mapObj.setFitView();}
//
回调函数
function
geocoder_CallBack(data) {
var
address;
//
返回地址描述
address
=
data.regeocode.formattedAddress;
//
返回结果拼接输出
document.getElementById(
"
iAddress
"
).innerHTML
=
address;}
//
鼠标点击,获取经纬度坐标
function
getLnglat(e){ mapObj.clearMap();
var
x
=
e.lnglat.getLng();
var
y
=
e.lnglat.getLat(); document.getElementById(
"
lnglat
"
).innerHTML
=
x
+
"
"
+
y; lnglatXY
=
new
AMap.LngLat(xy); geocoder();}
</
script
>
</
html
>
打开以后,是这样的:
点击一下地图,便可得到GCJ-02坐标,地址: