之前用的百度多,高德感觉差不多
var pointsArr = [
[116.362209, 39.887487],
[116.422897, 39.878002],
[116.372105, 39.90651],
[116.428945, 39.89663]
];
//每次请求做多40个点
AMap.convertFrom(pointsArr, 'gps', function(status, result){
convertCallback(status, result);
})
//回调函数
function convertCallback(status, result) {
if (status=='error') {
layer.msg("地图坐标转换错误!", {icon: 2});
return;
}
if (result.info === 'ok') {
var pointArr = result.locations;
if (0 == pointIndex) { //转换后计算
maxLng = pointArr[0].lng;
minLat = pointArr[0].lat;
}
}
}
/**
* 纠偏请求坐标格式
* tm参数传入存在问题,第一个元素的tm值为从1970年开始的unix的时间戳, 精确到秒,
* 其余元素的tm值为当前采集点的时间减去第一个元素的采集时间的差值。(一开始直接取成时间戳,纠偏报异常,数据库
* 查询是根据tm排序直接用了rownum替换
* 直接用rownum 发现了一个纠偏错误的地方, 但是我用实际时间戳减出来的值纠偏一直报错. 最后试2小时吧rownum
* 乘以10 反而纠偏的轨迹是对的了)
* 测试时有个订单的抓取的时间间隔太长, 纠偏无法规划路线
*/
var correctPointArry = [
{"x": 117.635982, "y": 36.696961, "sp": 0, "ag": 128, "tm": 1478031031}
, {"x": 117.635982, "y": 36.696961, "sp": 0, "ag": 128, "tm": 2}
,{"x": 117.635821, "y": 36.697116, "sp": 0, "ag": 15, "tm": 3}
,{"x": 117.635914, "y": 36.697266, "sp": 0, "ag": 15, "tm": 4}
,{"x": 117.635914, "y": 36.697266, "sp": 0, "ag": 15, "tm": 5}
,{"x": 117.611242, "y": 36.67224, "sp": 30, "ag": 284, "tm": 6}
,{"x": 117.606902, "y": 36.673317, "sp": 65, "ag": 287, "tm": 7}
,{"x": 117.601149, "y": 36.674796, "sp": 68, "ag": 288, "tm": 8}
,{"x": 117.595432, "y": 36.676315, "sp": 68, "ag": 287, "tm": 9}
,{"x": 117.589239, "y": 36.677907, "sp": 69, "ag": 287, "tm": 10}
, {"x": 117.5836, "y": 36.679367, "sp": 69, "ag": 287, "tm": 11}
, {"x": 117.578022, "y": 36.680809, "sp": 61, "ag": 287, "tm": 12}
, {"x": 117.573092, "y": 36.682101, "sp": 47, "ag": 287, "tm": 13}]
//一次最多400点求情
graspRoad.driving(correctPointArry,function(error,result) {
correctCallback(error, result);
});
//回调函数
function correctCallback(error, result) {
if (!error) { //成功时error为null
var path2 = [];
var newPath = result.data.points;
}
}
var map = new AMap.Map('container');
var newLine = new AMap.Polyline({
path: correctPoints,
strokeWeight: 5,
strokeOpacity: 0.8,
strokeColor: '#009688',
showDir: true
})
map.add(newLine)
ajax获取的数据是带顺序的,转换或纠偏怕数据返回时间不一样,最好分组递归查询再统一画线
newLine.show(); //显示
newLine.hide(); //隐藏
// 两条线的按钮 设置在最上边 z-index:
<div id='maptitle' style="float: left;padding: 30px;position: absolute;z-index: 998">
<p class="mapp" onclick="dbonclick()">
<button id="dbid" type="button" class="layui-btn layui-btn-danger mapbuttion" >button>
<strong>司机轨迹strong>
p>
<p class="mapp" onclick="cbonclick()">
<button id="cbid" type="button" class="layui-btn mapbuttion">button>
<strong>车辆轨迹strong>
p>
div>
<div id="container" style="width: 100% ;height: 890px;">div>
var maxLng = 0; //最大经度
var minLng = 0; //最小经度
var maxLat = 0; //最大纬度
var minLat = 0; //最小纬度
//循环点时获取
if (v.lon > maxLng) maxLng = v.lon;
if (v.lon < minLng) minLng = v.lon;
if (v.lat > maxLat) maxLat = v.lat;
if (v.lat < minLat) minLat = v.lat;
// (从网上复制)
/**
* 设置中心点和层级
* @param pointslength
*/
function setZoom(pointslength,poliyType) {
if (pointslength > 0) {
var cenLng = (parseFloat(maxLng) + parseFloat(minLng)) / 2;
var cenLat = (parseFloat(maxLat) + parseFloat(minLat)) / 2;
var zoom = getZoom(maxLng, minLng, maxLat, minLat);
map.setCenter([cenLng, cenLat]);//设置中心点
map.setZoom(zoom); //设置地图层级
if ('car' == poliyType) {
carCenterPoint = [cenLng, cenLat];
carZoom = zoom;
}else if ('driver' == poliyType) {
driverCenterPoint = [cenLng, cenLat];
driverZoom = zoom;
}
} else {
//没有坐标,显示全中国
map.setCenter([103.388611, 35.563611]);//设置中心点
map.setZoom(zoom); //设置地图层级
}
}
//根据经纬极值计算绽放级别。 (从网上复制)
function getZoom(maxLng, minLng, maxLat, minLat) {
var zoom = ["50", "100", "200", "500", "1000", "2000", "5000", "10000", "20000", "25000", "50000", "100000", "200000", "500000", "1000000", "2000000"]; // 级别18到3。
var p1 = new AMap.LngLat(maxLng, maxLat)
var p2 = new AMap.LngLat(minLng, minLat)
//计算两个点的距离
var distance = Math.round(p1.distance(p2));
for (var i = 0, zoomLen = zoom.length; i < zoomLen; i++) {
if (zoom[i] - distance > 0) {
let j = 3;
return 18 - i + j; //之所以会多3,是因为地图范围常常是比例尺距离的10倍以上。所以级别会增加3。
}
}
return 6;
}
var map = new AMap.Map('container');
AMap.plugin([
'AMap.ToolBar',
], function(){
// 在图面添加工具条控件,工具条控件集成了缩放、平移、定位等功能按钮在内的组合控件
map.addControl(new AMap.ToolBar({
// 简易缩放模式,默认为 false
liteStyle: true
}));
});
var pointsArry = [];
var maxLng = 0;
var minLng = 0;
var maxLat = 0;
var minLat = 0;
var lwFlage = false;
var carLine = null;
var drvierLine = null;
var carCenterPoint = null;
var carZoom = null;
var driverCenterPoint= null;
var driverZoom= null;
var graspRoad = new AMap.GraspRoad();
var carPathParam=[] ;
var carPoints;
var driverPoints;
var sIndexs = null;
//初始化百度地图
function initBaiduMap() {
sIndexs = layer.msg('地图轨迹生成中,请稍后...', {icon: 16, shade: [0.5, '#f5f5f5'], scrollbar: false, offset: 'auto', time: 0});
$.ajax({
url: baseUrl + "pmslocusinfo/getMapOrderbyGtm",
type: "post",
dataType: "json",
data: {waybillNum: '${param.waybillNum}', carNum: '${pwi.carNum}'},
async: false,
success: function (result) {
var pointMap = result.data;
carPoints = pointMap['car'];
driverPoints = pointMap['driver']; //司机是app端提交的高德系坐标不需要处理
createDriverPoints(driverPoints);
createCarPoints(carPoints,cardl.loadWeight);
},
error: function (result) {
$("#container").text("轨迹查询异常! ")
layer.close(sIndexs)
}
});
}
//统计车辆坐标点
function createCarPoints(points,loadWeight) {
if (points.length > 0) {
if (parseFloat(loadWeight) / 1000 >= 4.5) {
lwFlage = true;
var total = 0; //总记录数
var groupCount = 0; //每次转十条
if (points.length % 40 > 0) {
groupCount = parseInt(points.length / 40) + 1;
} else {
groupCount = parseInt(points.length / 40);
}
for (var i = 0; i < groupCount; i++) { //外层循环,有多少组四十条
var pos = []
for (var j = 0; j < 40; j++) { //内层循环,每组四十条
let pointCount = 0;
if (i > 1) {
pointCount = (i * 40) + j - 1;
} else {
pointCount = (i * 40) + j;
}
if (total < points.length) { //不超过总记录数结束
pos.push([
points[pointCount].lon,
points[pointCount].lat
]);
}
total++;
}
pointsArry[i] = pos;
}
convertCoordinates(pointsArry);
} else {
let pointArr = [];
$.each(points, function (i, v) {
pointArr.push([
v.lon, v.lat
]);
carPathParam.push({
'x':v.lon,
'y':v.lat,
"sp":v.spd,
"ag":v.agl,
"tm":v.gtm
})
});
createAMap(pointArr,'#009688','car');
map.setCenter(driverCenterPoint);
map.setZoom(driverZoom);
layer.close(sIndexs)
}
}else{
layer.close(sIndexs)
}
}
/**
* 坐标转换
* @param points
*/
var converPointsArr = [];
var pointIndex = 0;
function convertCoordinates(pointsArr) {
AMap.convertFrom(pointsArr[pointIndex], 'gps', function(status, result){
convertCallback(status, result);
})
}
//坐标转换回调函数
function convertCallback(status, result) {
if (status=='error') {
layer.msg("地图坐标转换错误!", {icon: 2});
return;
}
if (result.info === 'ok') {
var pointArr = result.locations;
if (0 == pointIndex) { //转换后计算
maxLng = pointArr[0].lng;
minLng = pointArr[0].lng;
maxLat = pointArr[0].lat;
minLat = pointArr[0].lat;
}
$.each(pointArr, function (i, v) {
converPointsArr.push([
v.lng, v.lat
]);
if (v.lng >= maxLng) maxLng = v.lng;
if (v.lng <= minLng) minLng = v.lng;
if (v.lat >= maxLat) maxLat = v.lat;
if (v.lat <= minLat) minLat = v.lat;
});
}
pointIndex++;
if (pointIndex < pointsArry.length) {
convertCoordinates(pointsArry);
} else {
//转换完成
//组装纠偏数据
assembleCorrectionData(converPointsArr)
}
}
//坐标轨迹纠偏数据整合
function assembleCorrectionData(beforeList,) {
for (let x in beforeList) {
carPathParam.push({
"x":beforeList[x][0],
"y":beforeList[x][1],
"sp":parseInt(carPoints[x].spd),
"ag":parseInt(carPoints[x].agl),
"tm":parseInt(carPoints[x].gtm)
})
}
groupCorrectPoints(carPathParam);
}
var correctPointArry = [];
//分组轨迹纠偏数据点 每次提交做多400个
function groupCorrectPoints(pointss) {
var flage=400;
var groupCount = 0;
if (pointss.length % flage > 0) {
groupCount = parseInt(pointss.length / flage) + 1;
} else {
groupCount = parseInt(pointss.length / flage);
}
for (var i = 0; i < groupCount; i++) {
let bIndex =i*flage;
let eIndex =(i+1)*flage-1
let pos = pointss.slice(bIndex, eIndex);
pos[0].tm=1478031031;
correctPointArry[i]=pos;
}
console.log(correctPointArry);
correctLocus(correctPointArry);
}
var correctIndex=0 ;
var correctPoints = [];
//高德轨迹纠偏请求
function correctLocus(pointArry) {
graspRoad.driving(correctPointArry[correctIndex],function(error,result) {
correctCallback(error, result);
});
}
//轨迹纠偏回调函数
function correctCallback(error, result) {
if (!error) {
var path2 = [];
var newPath = result.data.points;
if (0 == correctIndex) { //转换后计算
maxLng = newPath[0].x;
minLng = newPath[0].x;
maxLat = newPath[0].y;
minLat = newPath[0].y;
}
for (var i = 0; i < newPath.length; i += 1) {
correctPoints.push([newPath[i].x, newPath[i].y]);
if (newPath[i].x > maxLng) maxLng = newPath[i].x;
if (newPath[i].x < minLng) minLng = newPath[i].x;
if (newPath[i].y > maxLat) maxLat = newPath[i].y;
if (newPath[i].y < minLat) minLat = newPath[i].y;
}
correctIndex++
if (correctIndex < correctPointArry.length) {
//递归
correctLocus(correctPointArry);
} else {
//画车辆轨迹
var newLine = new AMap.Polyline({
path: correctPoints,
strokeWeight: 8,
strokeOpacity: 0.8,
strokeColor: '#009688',
showDir: true
})
map.add(newLine)
map.setFitView()
setZoom(correctPoints.length,'car');
carLine=newLine;
map.setCenter(driverCenterPoint);
map.setZoom(driverZoom);
layer.close(sIndexs)
}
}
}
/**
* 渲染司机轨迹
* @param points
*/
function createDriverPoints(points) {
if (points.length > 0) {
maxLng = points[0].lon;
minLng = points[0].lon;
maxLat = points[0].lat;
minLat = points[0].lat;
let pointArr = [];
$.each(points, function (i, v) {
let point=[]
pointArr.push([
v.lon, v.lat
]);
if (v.lon > maxLng) maxLng = v.lon;
if (v.lon < minLng) minLng = v.lon;
if (v.lat > maxLat) maxLat = v.lat;
if (v.lat < minLat) minLat = v.lat;
});
createAMap(pointArr,"#FF5722",'driver');
}
}
/**
* 渲染高德地图轨迹
* @param pointArr
* @param lineColor
* @param poliyType
*/
function createAMap(pointArr,lineColor,poliyType) {
setZoom(pointArr.length,poliyType);
if ('car' == poliyType) {
//carLine=polyline;
}else if ('driver' == poliyType) {
var polyline = new AMap.Polyline({
path: pointArr, //设置线覆盖物路径
strokeColor: lineColor, //线颜色
strokeWeight: 8, //线宽
strokeStyle: "solid", //线样式
showDir: true,
strokeOpacity:0.8,
});
drvierLine = polyline;
map.add(polyline);
}
layer.close(sIndexs)
}
// (从网上复制)
/**
* 设置中心点和层级
* @param pointslength
*/
function setZoom(pointslength,poliyType) {
if (pointslength > 0) {
var cenLng = (parseFloat(maxLng) + parseFloat(minLng)) / 2;
var cenLat = (parseFloat(maxLat) + parseFloat(minLat)) / 2;
var zoom = getZoom(maxLng, minLng, maxLat, minLat);
map.setCenter([cenLng, cenLat]);//设置中心点
map.setZoom(zoom); //设置地图层级
if ('car' == poliyType) {
carCenterPoint = [cenLng, cenLat];
carZoom = zoom;
}else if ('driver' == poliyType) {
driverCenterPoint = [cenLng, cenLat];
driverZoom = zoom;
}
} else {
//没有坐标,显示全中国
map.setCenter([103.388611, 35.563611]);//设置中心点
map.setZoom(zoom); //设置地图层级
}
}
//根据经纬极值计算绽放级别。 (从网上复制)
function getZoom(maxLng, minLng, maxLat, minLat) {
var zoom = ["50", "100", "200", "500", "1000", "2000", "5000", "10000", "20000", "25000", "50000", "100000", "200000", "500000", "1000000", "2000000"]; // 级别18到3。
var p1 = new AMap.LngLat(maxLng, maxLat)
var p2 = new AMap.LngLat(minLng, minLat)
var distance = Math.round(p1.distance(p2)); //计算两点间的距离
for (var i = 0, zoomLen = zoom.length; i < zoomLen; i++) {
if (zoom[i] - distance > 0) {
let j = 3;
return 18 - i + j; //之所以会多3,是因为地图范围常常是比例尺距离的10倍以上。所以级别会增加3。
}
}
return 6;
}
//司机轨迹图标点击事件
function dbonclick() {
if (drvierLine != null) {
let css = $("#dbid").attr("class");
if (css.indexOf("layui-btn-primary") != -1) {
map.setCenter(driverCenterPoint);//设置中心点
map.setZoom(driverZoom);
drvierLine.show();
$("#dbid").attr("class", "layui-btn layui-btn-danger mapbuttion")
} else {
drvierLine.hide();
$("#dbid").attr("class", "layui-btn layui-btn-primary mapbuttion")
}
} else {
layer.alert('暂无轨迹坐标数据!', {icon: 5});
}
}
//车辆轨迹图标点击事件
function cbonclick() {
if (carLine != null) {
let css = $("#cbid").attr("class")
if(css.indexOf("layui-btn-primary") !=-1){
map.setCenter(carCenterPoint);//设置中心点
map.setZoom(carZoom);
carLine.show();
$("#cbid").attr("class","layui-btn mapbuttion")
}else{
carLine.hide();
$("#cbid").attr("class","layui-btn layui-btn-primary mapbuttion")
}
}else {
layer.alert('暂无轨迹坐标数据!', {icon: 5});
}
}