[Vue 项目技巧] H5 百度地图点击获取坐标

306 阅读1分钟

背景

项目中引入了百度地图,但发现地图的 click 事件在 H5 没反应,查找一番发现原因是在移动端百度地图不支持 click 事件。

touchstart 与 touchend

那么就需要使用 TouchEvent 来实现,因为要区分点击、滑动、缩放,需要通过计算触屏位移和持续时间来判断是不是点击,监听 touchstart 记录触屏起始位置和开始时间,监听 touchend 计算触屏从开始到离开的位移和时长,一般来说时长很短(小于300ms)且位移为0(即起始位置和离开位置在一个点)才是点击,但考虑到某些机型可能会有细微偏移,可以允许一定的误差。

renderBMap() {
  // 实例化地图
  this.bmap = new window.BMap.Map('bmap-container')

  // 区分点击、滑动和缩放事件
  let time, startX, startY

  this.bmap.addEventListener('touchstart', e => {
    // 记录触屏起始位置和开始时间
    time = Date.now()
    startX = e.targetTouches[0].pageX
    startY = e.targetTouches[0].pageY
  })

  this.bmap.addEventListener('touchend', e => {
    // 计算触屏从开始到离开的位移和时长
    const endX = e.changedTouches[0].pageX
    const endY = e.changedTouches[0].pageY
    if (
      Date.now() - time < 300 &&
      Math.abs(endX - startX) < 5 &&
      Math.abs(endY - startY) < 5
    ) {
      // 点击地图
      this.bmap.clearOverlays()
      const bPoint = new window.BMap.Point(e.point.lng, e.point.lat)
      this.bmap.addOverlay(new window.BMap.Marker(bPoint))
      const convertor = new window.BMap.Convertor()
      // 5-百度坐标(bd09ll)转 3-火星坐标(gcj02)
      convertor.translate([bPoint], 5, 3, data => {
        doSomething(data.points[0].lat, data.points[0].lng)
      })
    }
  })
}

targetTouches 与 changedTouches

  • touches:当前屏幕上所有触摸点的列表
  • targetTouches:当前对象上所有触摸点的列表
  • changedTouches:涉及当前(引发)事件的触摸点的列表

  • touchstart 和 touchmove 使用:e.targetTouches[0].pageX
  • touchend 使用:e.changedTouches[0].pageX