2015年3月2日星期一

调用google map API的两个小 问题

任务如下:设计一个网页,提供输入框,由用户输入起始地址。目的地址是一个下拉框,里面是BCIT的5个校区。界面上还有1个“get directions”的按钮。用户输入起始、目的地址后,点击按钮,界面就显示地图和路线说明。如图:


实现起来也比较容易:
1、在html文件中包含jQuery和google MAP。



2、调用google.maps.Geocoder()方法获取用户输入起始地址的经纬度。目标地址的经纬度可以事先查好,写到下拉列表的value中去。调用可参考谷歌地图定位服务编程接口

3、使用起始、目的地址为参数,调用google map的direction service,来获取路线图和路线说明。调用可参考谷歌地图路线服务编程接口

然后就可以了。但出现了2个问题:1)选取不同的起始地、目的地,重新获取路线时,以前地路线图和路线说明没有清除,仍旧留在地图上。看上去很乱。2)刷新页面,第一次点击“获取路线”按钮时,系统仅绘出2个地标,却没有绘制路线图和路线说明。此后再点击则是正常的。

问题1 的原因在于把语句directionsDisplay = new google.maps.DirectionsRenderer()放入了点击获取路线按钮所调用的函数中,把它放入到页面的初始化函数中仅调用一次。得以解决。

问题2 的原因是调用Geocode方法时,对它的返回值处理不当。因为Ajax是异步调用,获取起始地址的经纬度还没有从服务器端得到响应时,程序就继续向下处理了。所以后面调用获取路线时,服务器就会抱怨没有提供起始地址。解决起来也简单:把调用路线服务的代码放入到调用Geocode方法的callback中就可以了。即:

 geocoder.geocode({'address': address}, function(results, status) {
        
        var location = results[0].geometry.location;
        var startLatlng = new google.maps.LatLng(location.lat(), location.lng());
        addMarker(startLatlng);
             
        // Create a new Marker object for destination.
        var endAddress = $( "#selectCampus").val();
        var endLat = endAddress.substring(0, endAddress.indexOf(','));
        var endLng = endAddress.substring(endAddress.indexOf(',') + 1); 
        endLatlng = new google.maps.LatLng(endLat, endLng);
        addMarker(endLatlng);

        var request = {
            origin:startLatlng,
            destination:endLatlng,
            travelMode: google.maps.TravelMode.DRIVING
        };

        directionsService.route(request, function(result, status) {
            if (status == google.maps.DirectionsStatus.OK) {
              directionsDisplay.setDirections(result);
            }
            else {
                alert('Directions Service was not successful for the following reason: ' + status);
            }
        });
    });

代码中标示为绿色的部分代码就是调用路线服务所用。如果把这部分代码移到这个函数之外,就会出现异步调用的问题。


没有评论: