最近在react項目中使用百度地圖,而且頁面集合了百度地圖的多種功能,感覺還是蠻復雜的,研究了很長時間,大概是把需要用到的東西都做了一遍。首先,因為react的生命周期機制以及webpack的模塊化開發,導致百度地圖很難引入到react中並使用,查看了網上很多方法,最后自己總結了一套自己的方法,感覺還挺好用。
我們需要在componentDidMount這個生命周期中初始化百度地圖,因為這個生命周期是render過一次結構了的,所以能查找到結構中的id為myMap的div不至於導致報錯
componentDidMount(){ //SK碼由於是項目注冊的,不公開使用,所以我刪掉了兩位字母,如果需要的請自行到百度地圖API官網注冊 this.MP('mYF2apbdwjfuo3HikGbZp5xNva8Q').then(BMap => { let map = new BMap.Map('myMap') let pointSelf; // 本人位置坐標 let point1 = new BMap.Point(113.26680951558,23.181518836079); // 默認本人位置坐標 let point2 = new BMap.Point(113.26650951558,23.181518836079) // 起點坐標 let point3 = new BMap.Point(113.26640951558,23.182818836079) // 終點坐標 //手機定位本人位置 let geolocation = new BMap.Geolocation(); new Promise((resolve, reject)=>{ geolocation.getCurrentPosition(function(r){ if(this.getStatus() == BMAP_STATUS_SUCCESS){ resolve(r) }else{ reject() } }) }).then( r => { map.panTo(r.point); map.centerAndZoom(r.point, 18) map.enableScrollWheelZoom() pointSelf = r.point; let lat=r.point.lat; let lon=r.point.lng; console.log(lat,lon,'本人坐標點') //人物位置藍色范圍圓圈 let blueBg = new BMap.Icon(blue, new BMap.Size(120,120)); let marker = new BMap.Marker(pointSelf,{icon:blueBg}); // 創建標注 map.addOverlay(marker); //人物位置 let myIcon = new BMap.Icon(self, new BMap.Size(35,35)); let marker1 = new BMap.Marker(pointSelf,{icon:myIcon}); // 創建標注 map.addOverlay(marker1); if(r.accuracy==null){ alert("無法獲取您的精確定位,請清理緩存后重新定位!"); return false; //用戶拒絕地理位置授權 } }).catch(function(){ map.centerAndZoom(point1, 18) map.enableScrollWheelZoom(); //人物位置藍色范圍圓圈 let blueBg = new BMap.Icon(blue, new BMap.Size(120,120)); let marker = new BMap.Marker(point1,{icon:blueBg}); // 創建標注 map.addOverlay(marker); //人物位置 let myIcon = new BMap.Icon(self, new BMap.Size(35,35)); let marker1 = new BMap.Marker(point1,{icon:myIcon}); // 創建標注 map.addOverlay(marker1); map.setViewport([new BMap.Point(113.26650951558,23.181518836079),new BMap.Point(113.26640951558,23.182818836079)]) }) //起點坐標 let startIcon = new BMap.Icon(start, new BMap.Size(40,75)); let marker2 = new BMap.Marker(point2,{icon:startIcon}); // 創建標注 map.addOverlay(marker2); //終點坐標 let endIcon = new BMap.Icon(end, new BMap.Size(40,75)); let marker3 = new BMap.Marker(point3,{icon:endIcon}); // 創建標注 map.addOverlay(marker3); //起點坐標添加文字標簽 var opts2 = { position : point2, // 指定文本標注所在的地理位置 offset : new BMap.Size(26, 15) //設置文本偏移量 } var label2 = new BMap.Label("股份樓", opts2); // 創建文本標注對象 label2.setStyle({ color : "#333", fontSize : "16px", fontWeight:'bold', background:'none', textShadow:'0 0 4px #fff', border:'0' }); marker2.setLabel(label2) //終點坐標添加文字標簽 var opts3 = { position : point3, // 指定文本標注所在的地理位置 offset : new BMap.Size(26, 15) //設置文本偏移量 } var label3 = new BMap.Label("醫院", opts3); // 創建文本標注對象 label3.setStyle({ color : "#333", fontSize : "16px", fontWeight:'bold', background:'none', textShadow:'0 0 4px #fff', border:'0' }); marker3.setLabel(label3) //起點和終點之間的線 // var driving = new BMap.DrivingRoute(map, {renderOptions:{map: map, autoViewport: true}}); //駕車實例 // driving.search(point2, point3); //添加放大縮小控件 var nav_size = new BMap.Size(20, 20) //地圖導航控件的參數 var navControl = new BMap.NavigationControl({ anchor: BMAP_ANCHOR_BOTTOM_RIGHT, offset: nav_size, type: 3, }) map.addControl(navControl) //添加左下角定位按鈕 var geolocationControl = new BMap.GeolocationControl({ offset: nav_size, }) //監聽左下角按鈕定位 geolocationControl.addEventListener('locationSuccess', function(e) { // 定位成功事件 var address = '' address += e.addressComponent.province address += e.addressComponent.city address += e.addressComponent.district address += e.addressComponent.street address += e.addressComponent.streetNumber console.log('當前定位地址為:' + address) }) geolocationControl.addEventListener('locationError', function(e) { // 定位失敗事件 console.log(e.message) }) //map.addControl(geolocationControl) //添加左下角定位按鈕 // var lushu; // // 實例化一個駕車導航用來生成路線 // var drv = new BMap.DrivingRoute('北京', { // onSearchComplete: function(res) { // if (drv.getStatus() == BMAP_STATUS_SUCCESS) { // var plan = res.getPlan(0); // var arrPois =[]; // for(var j=0;j<plan.getNumRoutes();j++){ // var route = plan.getRoute(j); // arrPois= arrPois.concat(route.getPath()); // } // map.addOverlay(new BMap.Polyline(arrPois, {strokeColor: '#48a2fb'})); // setTimeout(function(){ // //map.setViewport(arrPois); // },1000) // } // } // }); // drv.search(new BMap.Point(113.26650951558,23.181518836079) // 起點坐標 // , new BMap.Point(113.26640951558,23.182818836079)); function driveline(myP1,myP2){ var driving = new BMap.DrivingRoute(map); //創建駕車實例 driving.search(myP1, myP2); //第一個駕車搜索 driving.setSearchCompleteCallback(function(){ var pts = driving.getResults().getPlan(0).getRoute(0).getPath(); //通過駕車實例,獲得一系列點的數組 var polyline = new BMap.Polyline(pts); map.addOverlay(polyline); }) } driveline(point2,point3) }) }
下面是MP函數創建script標簽引入百度API
MP(ak) { return new Promise(function(resolve, reject) { var script = document.createElement('script') script.type = 'text/javascript' script.dataset.name = 'map' script.src = `https://api.map.baidu.com/api?v=3.0&ak=${ak}&callback=init` //callback調用init函數。 document.head.appendChild(script) window.init = () => { resolve(BMap) } }) }