Bootstrap

天地图绘制区域图层

背景:

业务方要求将

原效果图
原效果图
参考效果图
最终实现效果

变更点:

1.将原有的高德地图改为天地图

2.呈现形式修改:加两层遮罩:半透明遮罩层mask+区域覆盖物mask

实现过程:

1.更换地图引入源

 <link rel="stylesheet" href="https://cdn.jsdelivr.net/npm/maptalks/dist/maptalks.css" />
  <script type="text/javascript" src="https://cdn.jsdelivr.net/npm/maptalks/dist/maptalks.min.js"></script>

2.天地图基本配置-tk

3.实用方法封装

1)初始化地图方法封装

/**
 * 初始化地图
 */
export const initMap = (dom: any) => {
  window.maptalksMap = new window.maptalks.Map(dom, mapOptions)
}

2)初始化底图

/**
 * 初始化底图
 */
export const initBaseLayer = () => {
  const baseLayer = new window.maptalks.TileLayer(mapLayers.baseLayer, {
    urlTemplate: TianDiTuTile,
    subdomains: ['1', '2', '3', '4', '5'],
    attribution:
      '&copy; <a target="_blank" href="http://www.tianditu.cn">Tianditu</a>'
  })
  window.maptalksMap.setBaseLayer(baseLayer)
}

3)初始化底图的地点文字标记

/**
 * 初始化底图的地点文字标记
 */
export const initBaseMarkLayer = () => {
  const baseMarkLayer = new window.maptalks.TileLayer(mapLayers.baseMarkLayer, {
    urlTemplate: TianDiTuMark,
    subdomains: ['1', '2', '3', '4', '5']
  })
  baseMarkLayer.addTo(window.maptalksMap)
}

4)设置半透明遮罩层mask,其中,maskGeoJSon为导出的高德数据

/**
 * 设置半透明遮罩层mask
 */
export const initMaskPolygonLayer = () => {
  const maskPolygonLayer = new window.maptalks.VectorLayer(
    mapLayers.maskLayer
  )
  const geojson: any = maskGeoJSon.features[0].geometry
  const wgsJson = gcoord.transform(geojson, gcoord.GCJ02, gcoord.WGS84);
  const polygons = window.maptalks.GeoJSON.toGeometry(
    wgsJson,
    (geometry: any) => {
      geometry.setSymbol({
        lineColor: '#01e0f1',
        lineWidth: 4,
        lineOpacity: 0.4,
        polygonFill: '#014493',
        polygonOpacity: 0.3
      })
    }
  )
  maskPolygonLayer.addGeometry(polygons)
  maskPolygonLayer.addTo(window.maptalksMap)
}

5)设置覆盖物-某区域轮廓

/**
 * 设置覆盖物-嘉善轮廓
 */
export const initAreaPolygonLayer = () => {
  const areaPolygonLayer = new window.maptalks.VectorLayer(
    mapLayers.areaPolygonLayer
  )
  const polygons = window.maptalks.GeoJSON.toGeometry(
    jiashanGeoJSon,
    (geometry: any) => {
      geometry.setSymbol({
        lineColor: '#01e0f1',
        lineWidth: 4,
        lineOpacity: 1,
        polygonFill: '#0e4d96',
        polygonOpacity: 0.8
      })
    }
  )
  areaPolygonLayer.addGeometry(polygons)
  areaPolygonLayer.addTo(window.maptalksMap)
}

6)设置地名

/**
 * 设置地名
 */
export const initAreaNameLayer = () => {
  const areaNameLayer = new window.maptalks.VectorLayer(mapLayers.areaNameLayer)
  jiashanTownCenter.forEach(item => {
    new window.maptalks.Marker(item.position, {
      symbol: {
        textName: item.name,
        textSize: 20,
        textFill: '#ccc'
      }
    }).addTo(areaNameLayer)
  })
  areaNameLayer.addTo(window.maptalksMap)
}

4.应用

useEffect(() => {
    if (amapDomRef.current) {
      initMap(amapDomRef.current) // 初始化地图
      initBaseLayer() // 初始化底图
      initBaseMarkLayer() // 初始化底图的地点文字标记
      // initBackgroundLayer()
      initMaskPolygonLayer() // 设置半透明遮罩层mask
      initAreaPolygonLayer() // 设置覆盖物-区域(某地区)轮廓
      initAreaNameLayer() // 设置地名
      const data: any[] = getAllRealSchoolByMap().map(c => {
        return {
          name: c.title,
          position: c.position,
          status: c.checkStatus
        }
      })
      setCampusSecurySchoolMarkerToMap(data) // 业务数据点
    }
  }, [amapDomRef])

运行效果:不理想,出现了白色间隙,后面找出原因是因为高德地图和天地图不是同个坐标系(因为高德地图是火星坐标,而天地图是wgs84墨卡托4490),所以从高德地图上拉取的数据在天地图上不能完全适配,就出现了这样的间隙。

高德:火星坐标

天地图:wgs84墨卡托4490

解决方案:用gcoord进行坐标转换,参考文章:高德地图更换天地图底图(坐标转换)—使用高德API(WMTS)_高德经纬度转天地图经纬度_❄️文宸er的博客-CSDN博客

const wgsJson = gcoord.transform(geojson, gcoord.GCJ02, gcoord.WGS84);

最后,附上接口文档

MapTalks手册:https://doc.maptalks.com/docs/style/symbols/

;