Google 地图 javascript API + HTML5 地理定位怪癖
我在使用 Google 地图 javascript API 和 HTML5 地理定位时遇到了一个相当奇怪的问题。
我执行了以下 onload:
var geocoder;
var map;
var latlng;
function initialize() {
if(navigator.geolocation){
navigator.geolocation.getCurrentPosition(function(position){
latlng = new google.maps.LatLng(position.coords.latitude,position.coords.longitude);
});
}else{
latlng = new google.maps.LatLng(geoip_latitude(),geoip_longitude());
}
geocoder = new google.maps.Geocoder();
var myOptions = {
zoom: 8,
center: latlng,
streetViewControl: false,
mapTypeId: google.maps.MapTypeId.HYBRID
};
map = new google.maps.Map(document.getElementById("map_canvas"), myOptions);
google.maps.event.addListener(map, 'click', function(event) {
placeMarker(event.latLng);
var latLong = String(event.latLng).replace('(', '');
latLong = latLong.replace(')', '');
$('#latlng').attr('value', latLong);
});
function placeMarker(location) {
if(undefined != initialize.marker){
initialize.marker.setMap(null);
}
initialize.marker = new google.maps.Marker({
position: location,
map: map
});
initialize.marker.setMap(map);
map.setCenter(location);
}
}
现在,如果浏览器支持地理定位,则应该执行以下操作:获取纬度+经度,创建地图,并显示以纬度+经度为中心的地图。
如果我使用 geoip_ 函数(maxmind),它工作得很好,但是地理定位有一个奇怪的问题:
如果代码按原样运行,谷歌地图显示显示为一个灰色框,没有地图,也没有控件。
如果我添加一个alert(); 后立即
if(navigator.geolocation){
navigator.geolocation.getCurrentPosition(function(position){
latlng = new google.maps.LatLng(position.coords.latitude,position.coords.longitude);
});
}else{
latlng = new google.maps.LatLng(geoip_latitude(),geoip_longitude());
}
地图显示
就好了。这是怎么回事?
I'm having a rather strange issue with the Google Maps javascript API and HTML5 geolocation.
I have the following executed onload:
var geocoder;
var map;
var latlng;
function initialize() {
if(navigator.geolocation){
navigator.geolocation.getCurrentPosition(function(position){
latlng = new google.maps.LatLng(position.coords.latitude,position.coords.longitude);
});
}else{
latlng = new google.maps.LatLng(geoip_latitude(),geoip_longitude());
}
geocoder = new google.maps.Geocoder();
var myOptions = {
zoom: 8,
center: latlng,
streetViewControl: false,
mapTypeId: google.maps.MapTypeId.HYBRID
};
map = new google.maps.Map(document.getElementById("map_canvas"), myOptions);
google.maps.event.addListener(map, 'click', function(event) {
placeMarker(event.latLng);
var latLong = String(event.latLng).replace('(', '');
latLong = latLong.replace(')', '');
$('#latlng').attr('value', latLong);
});
function placeMarker(location) {
if(undefined != initialize.marker){
initialize.marker.setMap(null);
}
initialize.marker = new google.maps.Marker({
position: location,
map: map
});
initialize.marker.setMap(map);
map.setCenter(location);
}
}
Now, what this should do is if the browser supports geolocation, get the lat+long, create a map, and display the map centered on the lat+long.
It works just fine if I use the geoip_ functions (maxmind), but the geolocation has a strange issue:
If the code is run as is, the google maps display shows up as a gray box with no map and no controls.
If I add an alert(); immediately after
if(navigator.geolocation){
navigator.geolocation.getCurrentPosition(function(position){
latlng = new google.maps.LatLng(position.coords.latitude,position.coords.longitude);
});
}else{
latlng = new google.maps.LatLng(geoip_latitude(),geoip_longitude());
}
the map displays just fine.
What's up with that?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
W3C Geolocation API 是异步的;您拥有的成功回调函数(设置变量
latlng
)不会立即被调用——浏览器需要一些时间来实际进行地理定位;事实上,如果用户花一些时间阅读隐私提示并决定是否授予权限,这个过程可能会花费很多秒。但与此同时,您的地图会立即加载。您可能会发现它与后面的警报一起使用,因为警报给了浏览器一些时间来完成地理定位过程并在调用加载地图的代码之前调用回调。 (不过,仅仅等待一两秒钟并不是一个好的解决方案:某些用户和浏览器在显示位置之前将花费比这更长的时间。)
解决方法:调用创建地图的函数(您需要封装之后的几乎所有内容)地理定位调用)并在
getCurrentPosition
的成功回调和 geoip else 分支中调用它。这样,只有在确保latlng
变量已正确填充后,您才会尝试加载地图。The W3C Geolocation API is asynchronous; the success callback function you have (which sets the variable
latlng
) won't be called immediately -- the browser requires some time to actually do the geolocating; in fact, if the user takes some time to read the privacy prompt and decide whether or not to give permission, this process could take many seconds. In the meantime though, your map is loaded immediately.You're probably finding that it works with an alert after it because the alert gives the browser some time to finish the geolocation process and call the callback before getting to the code that loads the map. (Just waiting a second or two isn't a good solution though: some users and browsers will take much longer than that before revealing location.)
To fix: call the function that creates the map (you'll want to encapsulate practically everything after the geolocation call) and call it both in the success callback for
getCurrentPosition
and in the geoip else branch. That way you'll only try to load the map after you're guaranteed that thelatlng
variable has been appropriately filled.今天早上我第一次解决了这个混乱的问题(老实说,我很惊讶地图 API 没有处理这个问题的函数)。这是我的解决方案: JSFIddle
I worked through this mess for the first time this morning (honestly I am surprised the maps API doesn't have a function to deal with this). Here is My Solution: JSFIddle