用谷歌地图和百度地图做了类似于地铁上给定出发点和目的点和当前所在位置的
效果。。由于谷歌地图api在国内被封的厉害,且每天调用超过25000次就要收费
估计一般公司都会采用百度地图api
1.先来谷歌的。
我用的版本是google map api v3。
由于谷歌地图在国内被禁的厉害,推荐使用goagent来解决吧。
代码及效果图如下。
![](https://img.laitimes.com/img/9ZDMuAjOiMmIsIjOiQnIsIyZwpmL0UTN38FM1cjNxczN1MTMvwVOw8CXxAzMxAjMvw1ckF2bsBXdvwFdl5mLuR2cj5Set1yZtl2Lc9CX6MHc0RHaiojIsJye.jpg)
<!DOCTYPE html>
<html>
<head>
<title>Google Maps JavaScript API v3 Example: Marker
Animations Loop</title>
<link href="/maps/documentation/javascript/examples/default.css" target="_blank" rel="external nofollow"
rel="stylesheet">
<script
src="http://maps.googleapis.com/maps/api/js?v=3.exp&sensor=false"></script>
<script>
//地图的中心
var center = new google.maps.LatLng(32.102208, 118.925946);
//总路线
var flightPath;
//已经过的路线
var flightPath_yes;
//未经过的路线
var flightPath_no;
//路线所有点坐标数组
var path = [];
//路线上经过的点坐标数组
var path_yes = [];
//路线上未经过的点坐标数组
var path_no = [];
//已经经过的标记的图标样式
var image_green = 'green.jpg';
var image_red = 'red.jpg';
//路线上的各个中间点
var markers = [];
//地图变量
var map;
//定义已经过线的类型(箭头)
var lineSymbol1 = {
path: google.maps.SymbolPath.FORWARD_CLOSED_ARROW
};
//定义未经过线的类型(圆形)
var lineSymbol2 = {
path: google.maps.SymbolPath.CIRCLE,
scale: 5,
strokeColor: '#393'
};
function initialize() {
var mapOptions = {
zoom :12,
mapTypeId :google.maps.MapTypeId.ROADMAP,
center :center,
scaleControl :true //比例控件
};
map = new google.maps.Map(document.getElementById('map_canvas'),
mapOptions);
}
function drop() {
if(markers.length != 0){
deleteOverlays();
}
//出发点坐标的字符串
var str_start = document.getElementById("p_start").value;
//目的点坐标的字符串,进行分解并创建该字符串对应的坐标
var str_end = document.getElementById("p_end").value;
var str_start_ary = str_start.split(",");
var str_end_ary = str_end.split(",");
//出发点和终点坐标
var pos_start = new google.maps.LatLng(parseFloat(str_start_ary[0]),parseFloat(str_start_ary[1]));
var pos_end = new google.maps.LatLng(parseFloat(str_end_ary[0]),parseFloat(str_end_ary[1]));
//开始点坐标放入数组
path_yes.push(pos_start);
path.push(pos_start);
//中间点坐标字符串
var centers = document.getElementsByName("p_center");
var sel_centers = document.getElementsByName("sel_center");
for(var i=0; i<centers.length; i++){
var val = trim(centers[i].value);
if(val!=""){
var str_center_ary = val.split(",");
var pos_center = new google.maps.LatLng(parseFloat(str_center_ary[0]),parseFloat(str_center_ary[1]));
//判断该点坐标是否已经经过
var is_pass = sel_centers[i].value;
path.push(pos_center);
if(is_pass=="1"){
//经过
path_yes.push(pos_center);
}
}
}
//结束点坐标放入数组并判断结束点是否已经经过
path.push(pos_end);
if(document.getElementById("sel_p_end").value=="1"){
path_yes.push(pos_end);
}
//在地图上画出坐标点对应的标志
for ( var i = 0; i < path.length; i++) {
addMarker(path[i]);
}
//绘制总路线
flightPath = new google.maps.Polyline( {
path :path,
strokeColor :"red",
strokeOpacity :1.0,
strokeWeight :3,
icons: [{
icon: lineSymbol1,
offset: '100%'
}]
});
//绘制已经经过的路线
flightPath_yes = new google.maps.Polyline( {
path :path_yes,
strokeColor :"green",
strokeOpacity :1.0,
strokeWeight :3,
icons: [{
icon: lineSymbol1,
offset: '100%'
}]
});
flightPath.setMap(map);
flightPath_yes.setMap(map);
/** 根据总的坐标数组和已经经过点的坐标数组来获得未经过点的坐标数组 */
for(var i=0; i<path.length; i++){
var pass = false;
for(var j=0; i<path_yes.length-1; i++){
if(path_yes[j]==path[i]){
pass = true;
break;
}
}
if(!pass){
path_no.push(path[i]);
}
}
//绘制未经过的路线
flightPath_no = new google.maps.Polyline( {
path :path_no,
strokeColor :"red",
strokeOpacity :1.0,
strokeWeight :3,
icons: [{
icon: lineSymbol2,
offset: '100%'
}]
});
flightPath.setMap(map);
flightPath_no.setMap(map);
}
/** 地图上添加标志 */
function addMarker(pos) {
//判断该点是否已经经过,经过则将地图上的标志样式进行改变
var exist = false;
for(var j=0; j<path_yes.length; j++){
if(path_yes[j] == pos){
exist = true;
break;
}
}
var marker = new google.maps.Marker( {
position :pos,
map :map,
draggable :false,
//icon:image_green,
animation :google.maps.Animation.DROP
});
//鼠标放在图标上的时候显示的信息
marker.setTitle(pos.toString());
//根据某坐标是否经过来设置图标的颜色
if(exist){
marker.setIcon(image_green);
}else{
marker.setIcon(image_red);
}
markers.push(marker);
// 每个图标点击后对应的信息框
var infowindow = new google.maps.InfoWindow({
content: pos.toString(),
maxWidth: 20
});
google.maps.event.addListener(marker, 'click', function() {
infowindow.open(map,marker);
});
}
/** 删除地图上的标志和路线 */
function deleteOverlays() {
if (markers) {
for (i in markers) {
markers[i].setMap(null);
}
markers.length = 0;
path_yes.length = 0;
path.length = 0;
path_no.length = 0;
flightPath.setPath(path);
flightPath_yes.setPath(path);
flightPath_no.setPath(path);
}
}
/** 线上点的动画效果 */
function animateCircle() {
var count = 0;
offsetId = window.setInterval(function() {
count = (count + 1) % 200;
var icons = flightPath_no.get('icons');
icons[0].offset = (count / 2) + '%';
flightPath_no.set('icons', icons);
}, 20);
}
/** 去除字符串两端空格 */
function trim(str){
return str.replace( /^\s*/, "").replace(/\s*$/,"");
}
</script>
</head>
<body οnlοad="initialize();animateCircle();">
<div id="map_canvas" style="width: 500px; height: 400px;">
map div
</div>
-----------------模拟数据---------------------<br />
出发 :<input type="text" id="p_start" value="32.136168,118.944963"><br />
途经1:<input type="text" name="p_center" value="32.125666,118.945285">
<select name="sel_center"><option value="0">未到达</option><option value="1">到达</option></select><br />
途经2:<input type="text" name="p_center" value="32.103493,118.939492">
<select name="sel_center"><option value="0">未到达</option><option value="1">到达</option></select><br />
途经3:<input type="text" name="p_center" value="">
<select name="sel_center"><option value="0">未到达</option><option value="1">到达</option></select><br />
目的 :<input type="text" id="p_end" value="32.086042,118.889431">
<select id="sel_p_end"><option value="0">未到达</option><option value="1">到达</option></select><br />
--------------------------------------
<br />
<button id="drop" οnclick="drop()">
获取路线
</button>
<button id="delete" οnclick="deleteOverlays()">
删除路线图标
</button>
</body>
</html>
2.百度地图(只简单的花了点和线)
<!DOCTYPE html>
<html>
<head>
<meta name="viewport" content="initial-scale=1.0, user-scalable=no" />
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>Hello, World</title>
<style type="text/css">
#container {
width: 600px;
height: 400px;
}
</style>
<script type="text/javascript" src="http://api.map.baidu.com/api?v=1.3"></script>
<script type="text/javascript">
//pass:是否经过 0:没有经过,1:已经经过,2:当前点
var BASEDATA = [
{title:"家",content:"红枫新村",point:"118.952457|32.143779",pass:1,icon:{w:21,h:21,l:0,t:0,x:6,lb:5},distance_total:10.1,distance_pass:0,distance_per:"0%"},
{title:"羊山公园",content:"羊山公园地铁站",point:"118.94022|32.103007",pass:2,icon:{w:21,h:21,l:0,t:0,x:6,lb:5},distance_total:10.1,distance_pass:4.2,distance_per:"40%"},
{title:"马群",content:"马群地铁站",point:"118.905888|32.084829",pass:0,icon:{w:21,h:21,l:0,t:0,x:6,lb:5},distance_total:10.1,distance_pass:8.3,distance_per:"83%"},
{title:"公司",content:"自己开的",point:"118.895289|32.091025",pass:0,icon:{w:21,h:21,l:0,t:0,x:6,lb:5},distance_total:10.1,distance_pass:10.1,distance_per:"100%"}
]
//默认地图地图的中点和缩放比例
var BASEDATA2 = {scale:13,point_center:"118.916812|32.109531"};
var map;
var json_passAry = [];//已经经过的点的json对象数组,包括当前点
var json_not_passAry = [];//没有经过的点的json对象数组,包括当前点
var point_passAry = [];
var point_not_passAry = [];
//将json数据解析,将坐标点信息归类放入已经过和未经过的数组中
for(var i=0; i<BASEDATA.length; i++){
var json = BASEDATA[i];
var point = new BMap.Point(json.point.split("|")[0],json.point.split("|")[1]);
if(json.pass==1){
json_passAry.push(json);
point_passAry.push(point);
}else if(json.pass==0){
json_not_passAry.push(json);
point_not_passAry.push(point);
}else if(json.pass==2){
json_passAry.push(json);
json_not_passAry.push(json);
point_passAry.push(point);
point_not_passAry.push(point);
}
}
//
var point_center = new BMap.Point(118.916812,32.109531)
window.onload = function() {
map = new BMap.Map("container");
var point_center = new BMap.Point(BASEDATA2.point_center.split("|")[0],BASEDATA2.point_center.split("|")[1]);
map.centerAndZoom(point_center, BASEDATA2.scale);
var opts = {
width : 250, // 信息窗口宽度
height : 100, // 信息窗口高度
title : "Hello" // 信息窗口标题
}
var infoWindow = new BMap.InfoWindow("World", opts); // 创建信息窗口对象
map.enableScrollWheelZoom(); //启用滚轮放大缩小
map.addControl(new BMap.NavigationControl()); //添加默认缩放平移控件
map.addControl(new BMap.ScaleControl()); // 添加默认比例尺控件
}
function fun1() {
map.clearOverlays();
//已经经过的点画线
var polyline_pass = new BMap.Polyline(point_passAry, {
strokeColor : "green",
strokeWeight : 2,
strokeOpacity : 0.8
});
//未经过的点画线
var polyline_not_pass = new BMap.Polyline(point_not_passAry, {
strokeColor : "red",
strokeWeight : 2,
strokeOpacity : 0.8
});
map.addOverlay(polyline_pass);
map.addOverlay(polyline_not_pass);
//已经经过的点画上标志(经过的为绿色,当前点为白色)
for(var i=0; i<BASEDATA.length; i++){
var marker;
var point = new BMap.Point(BASEDATA[i].point.split("|")[0],BASEDATA[i].point.split("|")[1]);
var label = new BMap.Label(BASEDATA[i].title,{"offset":new BMap.Size(9,-20)});
var icon;
if(BASEDATA[i].pass==2){
icon = new BMap.Icon("markers.png", new BMap.Size(20,20),{anchor: new BMap.Size(5,20),infoWindowAnchor:new BMap.Size(10,1),offset:new BMap.Size(6,21)});
}else if(BASEDATA[i].pass==1){
icon = new BMap.Icon("green.png", new BMap.Size(20,20),{anchor: new BMap.Size(5,20),infoWindowAnchor:new BMap.Size(10,1),offset:new BMap.Size(6,21)});
//marker = new BMap.Marker(point,{icon:icon});
}else if(BASEDATA[i].pass==0){
icon = new BMap.Icon("red.png", new BMap.Size(20,20),{anchor: new BMap.Size(5,20),infoWindowAnchor:new BMap.Size(10,1),offset:new BMap.Size(6,21)});
}
marker = new BMap.Marker(point,{icon:icon});
marker.setLabel(label);
map.addOverlay(marker); // 将标注添加到地图中
label.setStyle({
borderColor:"#808080",
color:"#333",
cursor:"pointer"
});
(function(){
var _json = BASEDATA[i];
var _iw = createInfoWindow(_json);
var _marker = marker;
_marker.addEventListener("click",function(){
this.openInfoWindow(_iw);
});
_iw.addEventListener("open",function(){
_marker.getLabel().hide();
});
_iw.addEventListener("close",function(){
_marker.getLabel().show();
});
label.addEventListener("click",function(){
_marker.openInfoWindow(_iw);
});
if(_json.pass==2){
label.hide();
_marker.openInfoWindow(_iw);
}
})();
}
//点移动
var aryAll = [];
if(point_not_passAry.length>0){
aryAll.push(point_not_passAry[0]);
}
for(var i=0; i<point_not_passAry.length-1; i++){
var ary = getPoints(point_not_passAry[i],point_not_passAry[i+1]);
aryAll = aryAll.concat(ary)
}
var move_marker;
var icon = new BMap.Icon("markers.png", new BMap.Size(20,20),{anchor: new BMap.Size(5,20),infoWindowAnchor:new BMap.Size(10,1),offset:new BMap.Size(6,21)});
move_marker = new BMap.Marker(aryAll[0],{icon:icon});
map.addOverlay(move_marker);
var move_i=0;
setInterval(function(){
move_marker.setPosition(aryAll[move_i++%aryAll.length]);
},300)
}
function createInfoWindow(json){
var iw;
if(json.pass==2){
iw = new BMap.InfoWindow("<b class='iw_poi_title' title=' 您当前的所在地:<br />" +json.title + "'>" + json.title + "</b><div class='iw_poi_content'>"+json.content+"<br />"
+"总公里数:"+json.distance_total+"km, 已经过的公里数:"+json.distance_pass+"km, 经过的百分比:"+json.distance_per+"</div>");
}else{
iw = new BMap.InfoWindow("<b class='iw_poi_title' title='" + json.title + "'>" + json.title + "</b><div class='iw_poi_content'>"+json.content+"</div>");
}
return iw;
}
/** 给定两个点获取两个点之间的中间点, */
function getPoints(p_begin,p_end){
var ary = [];
//ary.push(p_begin);//
var polyline = new BMap.Polyline([p_begin,p_end]);
var p_pass2 = polyline.getBounds().getCenter();
var polyline2 = new BMap.Polyline([p_begin,p_pass2]);
var p_pass1 = polyline2.getBounds().getCenter();
ary.push(p_pass1);//
ary.push(p_pass2);//
var polyline3 = new BMap.Polyline([p_pass2,p_end]);
var p_pass3 = polyline3.getBounds().getCenter();
ary.push(p_pass3);
ary.push(p_end);
return ary;
}
</script>
</head>
<body>
<div id="container"></div>
<input type="button" οnclick="fun1();" value="click me...">
</body>
</html>