使用百度地图 中心点和坐标偏移的问题

百度地图的引入

在index.html引入百度地图开发包如下:



  ……
  
    

若控制台有黄色警告
使用百度地图 中心点和坐标偏移的问题_第1张图片
建议改api为getscript即可


接着eslint报错BMap未定义,但是地图加载进来了能正常使用,只需配置eslint让其识别BMap这个全局变量,方法同cdn引入第三方包时的配置:
1、修改webpack.base.conf.js

externals: {
    'vue': 'Vue',
    'vue-router': 'VueRouter',
    ……
    'BMap': 'window.BMap'
  },

2、修改配置文件.eslintrc.js

globals: {
	'Vue': true,
    'VueRouter': true,
    ……
    'BMap': true
  }

至此可以正常创建一个地图div容器,初始化使用百度地图了,注意容器的高度宽度设置,否则地图可能显示不出来。

中心点和坐标偏移的问题

代码设置如下:

initMap () {
this.map = new BMap.Map('mapContent') // 在百度地图容器中创建一个地图
let point = new BMap.Point(113.331084, 23.112223) // 坐标点为广州塔
this.map.centerAndZoom(point, 12) // 设定地图的中心点和坐标并将地图显示在地图容器中
// 给地图上添加一个标注-广州塔
let cIcon = new BMap.Icon('/static/img/map/marker_' + state + '.png', new BMap.Size(20, 30))
let label = new BMap.Label(slabel, {offset: new BMap.Size(20, -10)})
let marker = new BMap.Marker(point, {icon: cIcon})
// 给label设置样式 display: 'none' label先不显示光标移动到其上才显示
label.setStyle({border: 'none', background: '#409eff', color: 'white', padding: '2px 4px'})
marker.setLabel(label)
/* eslint-disable */
// marker.setAnimation(BMAP_ANIMATION_BOUNCE) // 添加mark的动画效果 - 弹跳
/* eslint-enable */
this.map.addOverlay(marker) // 将标注添加到地图中
},

问题现象如下:

很明显广州塔标注位置不对,真正的广州塔也不在正中心展示。
放大地图后,标注位置跳到了正确位置。

说明坐标没有问题。如下存在两个问题:
1、centerAndZoom设置的中心点不在中心位置
2、初始化标注点位置存在偏离
一个个问题解决

1、centerAndZoom设置的中心点不在中心位置

很多人说是创建地图的时候div隐藏了?高宽为0?
但是我是在mounted后才创建的地图,照道理说这时候dom都已经挂载完了,再说了高宽为0初始化地图难道不报错吗?
陷入沉思……
于是我打印出dom的宽度发现

mounted () {
  this.initMap() // 创建和初始化地图
  /* setTimeout(() => {
    this.initMap() // 创建和初始化地图
  }, 2000) */
},
initMap () {
  this.map = new BMap.Map('mapContent') // 在百度地图容器中创建一个地图
  console.log(document.getElementById('mapContent').offsetHeight, 111)
  let point = new BMap.Point(113.331084,23.112223)
  ……
},

当未使用setTimeout延迟地图初始化时,打印出的宽度为1872px;
在使用了setTimeout延迟地图初始化后,打印出的宽度为1644px;
相差51px,虽说用setTimeout延迟加载即可解决问题,但是延迟时间不可控啊,根本原因也没查出来。
继续陷入沉思……
因为界面的布局是,左边菜单,点击相应菜单进入嵌入百度地图的子路由。于是修改左侧菜单的宽度……

// el-aside的宽度设置从220px改为420px后

当未使用setTimeout延迟地图初始化时,打印出的宽度为1872px;
在使用了setTimeout延迟地图初始化后,打印出的宽度为1444px;
也就是说,初始加载地图,其容器获取的高宽是几乎整个屏幕的高宽……
接着发现,未使用setTimeout延迟地图初始化时:
在el-aside选择菜单切换路由的时候,宽度打印1444px,中心点正常;
刷新当前地图所在路由页面时,宽度打印1872px,中心点偏离;
同时,在三个mounted里打印el-aside的宽度顺序发现

// 最外层路由 mounted () { console.log(document.getElementById('testaaa').offsetWidth, 'main') setTimeout(() => { console.log(document.getElementById('testaaa').offsetWidth, 'main') }, 1000) }, // el-aside左侧菜单中 mounted () { console.log(document.getElementById('testaaa').offsetWidth, 'el-aside') }, // 地图所在路由页面下 mounted () { console.log(document.getElementById('testaaa').offsetWidth, 'baidu-map') },

控制台打印结果如下:
0 “el-aside”
0 “baidu-map”
0 “main”
220 “main”
也就是说,地图加载的时候,菜单还没有获取到其宽度,大概是因为父级路由等所有加载完成后,才给菜单宽度赋值。
导致地图加载先于el-aside的菜单的宽度设置,所以地图容器div没有减去左边菜单的div宽度。
至于解决办法锁定在延迟地图的加载,于是在地图子路由下尝试:

mounted () {
  console.log(document.getElementById('mapContent').offsetWidth, 'baidu-map')
  setTimeout(() => {
    console.log(document.getElementById('mapContent').offsetWidth, 'baidu-map')
    this.initMap() // 创建和初始化地图
  }, 0)
},

查看控制台打印如下
在这里插入图片描述
调用setTimeout时,把函数参数,放到事件队列中。等主程序运行完,再调用。
导致setTimeout哪怕是0s后的函数都成功在父路由加载完成后才执行,成功解决了中心点偏离的问题。

2、初始化标注点位置存在偏离

第一个问题解决完后发现

!!!所有初始化标注点的位置都正确了

你可能感兴趣的:(vue)