1. 程式人生 > >百度地圖/高度地圖大批量座標轉換結果返回順序問題

百度地圖/高度地圖大批量座標轉換結果返回順序問題

  專案需求:裝置採集到的GPS座標資訊,需提供實時、歷史軌跡的檢視功能。這些點座標除經緯度資訊外還攜帶了其它的資訊,比如:速度、方向、解狀態等。原始的GPS座標需要轉換成百度地圖/高德地圖座標後才能在相應的地圖上顯示,否則存在較大的位置偏差。

  前端人員在高德地圖上顯示多個點座標資訊時,發現轉換後回來的座標點沒法與該座標點的其它資訊對應。一直得不到解決。

幫忙檢視,除錯程式碼。發現高德/百度地圖座標轉換方法是非同步的,包括js api和http請求的uri方式。

https://lbs.amap.com/api/javascript-api/reference/lnglat-to-address#t2 

http://lbsyun.baidu.com/index.php?title=webapi/guide/changeposition

可以看到該方法不支援傳參的擴充套件和屬性附帶。所以通過將座標的其它屬性附帶到座標的非同步轉換方法,再通過結果一起帶回來的辦法是行不通了。

方法是非同步的,回撥函式回撥就會有時間延遲。如果按照for迴圈順序去提交轉換,其回撥函式也不是順序執行的。

也就是說,你連續提交了1、2、3、4、5,5個GPS座標,其回撥函式的回撥順序有可能是43521,或其他,是無需的。

一次性傳一組座標進行轉換,回撥返回結果的座標數組裡面的順序也是改變了的。

最後通過遞迴解決。再次記錄下思路。

那麼我們如何保證返回結果有序?

  我們可以一次性轉換一個GPS座標,等回撥函式回撥成功後在地圖上新增覆蓋物,再進行下一個座標的轉換。依次保證資料順序不會亂。

以高德地圖為例,用簡單的程式碼模擬下:

<script type="text/javascript">
    var map = new AMap.Map('container', {
        zoom: 12,
        center: [121.532327,31.148761]
    });

    var a = [1,2,3,4,5,6,7,8];//模擬座標解狀態
    var OnlineLinArr = [
           new AMap.LngLat(121.528,31.1509),
           new AMap.LngLat(121.428,31.1503),
           
new AMap.LngLat(121.328,31.1505), new AMap.LngLat(121.468,31.1508), new AMap.LngLat(121.478,31.1506), new AMap.LngLat(121.488,31.1504), new AMap.LngLat(121.498,31.1502), new AMap.LngLat(121.418,31.1503), ]; var k = 0; function convertFrom(LngLat){ AMap.convertFrom(LngLat, 'gps', (status, result) => { console.log(status); var OnlinelngX,OnlinelatY,OnlineGDlngX,OnlineGDlatY; if(result.info === 'ok'){ var GDlinArr = result.locations; for (var i = 0; i < GDlinArr.length; i++) { OnlineGDlngX = GDlinArr[i].lng; OnlineGDlatY = GDlinArr[i].lat; } } if(status === 'complete'){ if(k < OnlineLinArr.length-1){ var j = ++k; console.log(a[j]); convertFrom(OnlineLinArr[j]); if(a[j] == 1){ ImgFunc('red.png',OnlineGDlngX,OnlineGDlatY); }else if(a[j] == 2){ ImgFunc('green.png',OnlineGDlngX,OnlineGDlatY); }else{ ImgFunc('startpoint.png',OnlineGDlngX,OnlineGDlatY); } } } }); } convertFrom(OnlineLinArr[k]); console.log(a[k]); function ImgFunc (img,x,y) { var marker = new AMap.Marker({ map:map, position:new AMap.LngLat(x, y),  icon:img,   // autoRotation:true, }); } </script>

如果此文對您有幫助,微信打賞我一下吧~