这是我参与2022首次更文挑战的第1天
获取某个地点的经纬度信息,在后台管理系统中是比较常见的,这次在开发中也有相应的需求,下面我把实现的思路和大家一起分享,写的不好的地方请大家多多指正!
1、下载 vue-baidu-map 模块
npm install vue-baidu-map --save
2、在 main.js 文件中全局引入
import BaiduMap from 'vue-baidu-map'
Vue.use(BaiduMap, {
ak: AK // 这里的AK是百度的密钥
})
3.在页面的组件中引入 BaiduMap
<el-dialog
title="经纬度选择"
:visible.sync="mapDialogVisible"
:close-on-click-modal="false"
width="50%"
>
<el-form label-position="right" label-width="120px">
<el-form-item label="详细地址">
<el-autocomplete
v-model="address"
:fetch-suggestions="kwSearch"
placeholder="请输入详细地址"
style="width: 100%"
:trigger-on-focus="false"
:debounce=0
@select="handleSelectAddress"
/>
</el-form-item>
</el-form>
<baidu-map class="map" :center="center" :zoom="zoom" @ready="handler" :scroll-wheel-zoom="true" @click="clickMap">
<bm-geolocation anchor="BMAP_ANCHOR_BOTTOM_RIGHT" :showAddressBar="true" :autoLocation="true"></bm-geolocation>
<bm-city-list anchor="BMAP_ANCHOR_TOP_LEFT"></bm-city-list>
</baidu-map>
<div slot="footer" class="dialog-footer">
<el-button @click="handleMapSubmit" type="primary">提交</el-button>
<el-button @click="mapDialogVisible = false">返回</el-button>
</div>
</el-dialog>
<script>
import loadBMap from '@/utils/loadBMap.js'
const AK = '你的百度密钥'
let local = null
export default {
data() {
return {
// 经纬度选择对话框
mapDialogVisible: false,
address: '',
longitude: null,
latitude: null,
center: {
lng: 113.27,
lat: 23.13
},
zoom: 15,
map: null,
BMap: null
}
},
async mounted() {
await loadBMap(AK)
},
methods: {
handler ({BMap, map}) {
this.map = map
this.BMap = BMap
let _this = this
// 调用百度地图api 中的获取当前位置接口
geolocation.getCurrentPosition(function (r) {
let myGeo = new BMap.Geocoder()
myGeo.getLocation(new BMap.Point(r.point.lng, r.point.lat), function (result) {
if (result) {
_this.showMap({lng: result.point.lng, lat: result.point.lat})
_this.longitude = result.point.lng
_this.latitude = result.point.lat
}
})
})
//开启鼠标滚轮缩放
this.map.enableScrollWheelZoom(true)
},
clickMap(e) {
this.removeAllMarker(this.map)
const point = e.point
const marker = new BMap.Marker(point)
this.map.addOverlay(marker)
this.longitude = point.lng
this.latitude = point.lat
},
// 清除地图上的所有覆盖物
removeAllMarker(map) {
if (map) {
let overlays = map.getOverlays()
overlays.forEach((marker, index, arr) => {
map.removeOverlay(marker)
})
}
},
// 提交按钮点击事件
handleMapSubmit() {
// 给经纬度赋值
this.rowFormTempData.lat = this.latitude;
this.rowFormTempData.lng = this.longitude;
// 关闭经纬度选择对话框
this.mapDialogVisible = false
},
// 根据输入的关键词进行搜索
kwSearch(keyword, callback) {
let options = {
onSearchComplete: function(results) {
if (local1.getStatus() === 0) {
// 判断状态是否正确
var temp = []
for (let i = 0; i < results.getCurrentNumPois(); i++) {
const x = results.getPoi(i)
const item = { value: x.address + x.title, point: x.point }
temp.push(item)
callback(temp)
}
} else {
callback([])
}
}
}
var local1 = new this.BMap.LocalSearch(this.map, options)
local1.search(keyword)
},
// 选中搜索建议项
handleSelectAddress(item) {
let { point } = item
this.latitude = point.lat
this.longitude = point.lng
this.showMap({lng: point.lng, lat: point.lat})
},
// 在地图上画点
showMap (point) {
setTimeout(() => {
//移除地图覆盖物
this.map.centerAndZoom(point, 15)
this.map.clearOverlays()
if (point && point.lng && point.lat) {
let marker = new BMap.Marker(point)
this.map.addOverlay(marker)
this.center = point
}
}, 500)
},
// 点击编辑时根据已有的经纬度信息在地图上画点
// 地图经纬度选择
handleMapSelect() {
this.mapDialogVisible = true;
this.address = '';
this.showMap({lng: this.rowFormTempData.lng, lat: this.rowFormTempData.lat})
},
},
}
</script>
在使用BaiduMap过程中,有可能会出现BMap is not defined 报错信息,所以页面引入了 loadBMap.js 文件就是用来解决 BMap is not defined 这个问题的。
具体代码如下:
/**
* 动态加载百度地图api函数
* @param {String} ak 百度地图AK,必传
*/
export default function loadBMap(ak) {
return new Promise(function(resolve, reject) {
if (typeof window.BMap !== 'undefined') {
resolve(window.BMap)
return true
}
window.onBMapCallback = function() {
resolve(window.BMap)
}
let script = document.createElement('script')
script.type = 'text/javascript'
script.src = 'http://api.map.baidu.com/api?v=3.0&ak=' + ak + '&callback=onBMapCallback'
script.onerror = reject
document.head.appendChild(script)
})
}
如果要去除地图左下角的版权和文字信息,可以在 style 里面加入以下的样式
<style scoped>
/deep/.BMap_cpyCtrl {
display: none !important;
}
/deep/.anchorBL {
display: none !important;
}
</style>
未加样式之前:
加了样式之后:
关于 vue-baidu-map 这个插件的使用,大家可以查阅官方文档!
vue-baidu-map 官网地址