vue 高德地图 多个标记点_react+高德地图实现热力地图及海量点加载

之前研究过研究过百度地图配合echarts实现热力地图和大量标注点加载,有兴趣可查看博客https://www.cnblogs.com/class1/p/13691867.html。结果效果不是太理想,进而转战高德地图。

最终效果图先展示一波。

07714a6aa455d0091fc225b40d7b34c2.png

图上效果图的实现主要有五点:

一,高德地图的引入。

引入地图,和百度地图一样,还是要申请自己使用的key值,网上讲解很多,这里不再细述。有了key值以后,在全局的入口html文件中引入高德地图,我使用的是antd pro框架,入口文件是document.ejs。如果不想申请key值,直接复制粘贴下面的就可以行。

然后直接在项目里创建页面文件,写你的地图就完了,非常方便。这里我创建的地图文件命名为guidemap.js.

二,热力地图的实现。

关键部分代码:

// 创建地图,gaoDe为地图容器标签的id名const map = new AMap.Map('gaoDe', {         resizeEnable: true,   // 允许缩放地图      center: [108.5, 34.3],  // 地图中心点经纬度      zoom: 4   // 地图的等级,范围是3~18级    });    let heatmap;    map.plugin(["AMap.Heatmap"], function () {      // 初始化heatmap对象      heatmap = new AMap.Heatmap(map, {        radius: 25, // 给定半径        opacity: [0, 0.8],        gradient:{    // 热力值的颜色设置,范围是0-1,可以分段设置颜色            0.5: 'blue',            0.65: 'rgb(117,211,248)',            0.7: 'rgb(0, 255, 0)',            0.9: '#ffea00',            1.0: 'red'        }      });      heatmap.setDataSet({        data: gaoData,  // heatmapData 热力地图的数据,这里的数据格式 [ {"lng": 116.191031,"lat": 39.988585,"count": 10},{...}]        max: 10   // 热力最大范围值      })    });

效果图如下:

8873675c2f033fd31f7a5a6a88c191c7.png

三,控件的添加。

关键部分代码:

    const scale = new AMap.Scale({        visible: true,        offset: new AMap.Pixel(70,20),   // 控件的偏移位置      });      map.addControl(scale);   // 添加比例尺控件      map.addControl(new AMap.ToolBar());   // 添加缩放控件

因为是热力图,一般图上会有个热力标尺,但是高德地图没有,可以将高德地图引入echarts图表中,通过配置项加热力标尺(visualMap属性)。但是考虑到高德地图的功能比较完备,为了一个属性引入echarts,太大费周章。今天我决定手写个热力标尺:

 
10

这个是在react项目里写的html,css样式这么写没问题的。

看下添加的控件效果:这个手写的热力标尺毫无违和感是不是。

6782a6ce83de0a4f50960655b45c85c1.png

四,海量点标记的添加。

// 海量点标记    const mass = new AMap.MassMarks(massData, {      opacity: 0.8,      zIndex: 111,      cursor: 'pointer',      style: {        url: 'https://webapi.amap.com/theme/v1.3/markers/n/mark_b.png',   // 点标注用的图片,可自定义        anchor: new AMap.Pixel(6, 6),   // 位置偏移        size: new AMap.Size(15, 15)   // 标注的大小      }    });  mass.setMap(map);

此时就是页面标注点和热力图结合了,但是标注点还没有添加信息窗,点击是没有效果的。如果标注点不是太多,也可以不用海量点,直接创建mark,每一个依次添加就行

 const allLength=gaoData.length;    // 获取标注点的个数     for(let i = 0; i < allLength; i += 1){    // 把每个点都添加在地图上     const marker = new AMap.Marker({        position: [gaoData[i].lng, gaoData[i].lat],      map:map       });     }

五,点标记的信息窗的添加。

点标记应该和上面的四合起来用的。如果是海量点,加信息窗如下:

const mass = new AMap.MassMarks(massData, {      opacity: 0.8,      zIndex: 111,      cursor: 'pointer',      style: {        url: 'https://webapi.amap.com/theme/v1.3/markers/n/mark_b.png',        anchor: new AMap.Pixel(6, 6),        size: new AMap.Size(15, 15)      }    });   //  这部分是label标签,使用label就是这样写的,使用这部分就要注释掉下面信息窗的代码    // var marker = new AMap.Marker({content: ' ', map: map});    // mass.on('mouseover', function (e) {    //   marker.setPosition(e.data.lnglat);    //   marker.setLabel({content: e.data.lnglat})    // });    const infoWindow = new AMap.InfoWindow({offset: new AMap.Pixel(0, -10)});    mass.on('click', function (e) {      infoWindow.setContent(`
标题:热点详细信息
地理位置:${e.data.lnglat.lng}, ${e.data.lnglat.lat}
最近三个月热力值:${e.data.val}
`); infoWindow.open(map, e.data.lnglat); }); mass.setMap(map);

这个是使用label标签的效果,鼠标放在mark标注上就展示当前点的地理位置坐标:

f6e26a01095cf104e8e9e81ed6eda8e6.png

如果点数不多这里提供了两种写法:

 const allLength=gaoData.length;    for(let i = 0; i < allLength; i += 1){      const marker = new AMap.Marker({        position: [gaoData[i].lng, gaoData[i].lat],        map:map      });      const infoWindow = new AMap.InfoWindow({        anchor: 'bottom-center',        content:`

这是信息窗体!这是信息窗体!

${gaoData[i].lng}

` , }); // 鼠标点击marker弹出自定义的信息窗体 marker.on('click', function () { infoWindow.open(map,[gaoData[i].lng, gaoData[i].lat]) }); }
 var infoWindow = new AMap.InfoWindow({offset: new AMap.Pixel(0, -30)});    const allLength=gaoData.length;    function markerClick(e) {      infoWindow.setContent(e.target.content);      infoWindow.open(map, e.target.getPosition());    }    for(let i = 0; i < allLength; i += 1){      const marker = new AMap.Marker({        position: [gaoData[i].lng, gaoData[i].lat],        map:map      });      marker.content = '我是第' + (i + 1) + '个Marker';      marker.on('click', markerClick);    }

最后附上完整的代码:

// guidemap.jsimport React, { Component,Fragment } from 'react';const {AMap} = window;class Guide extends Component {  constructor(props) {    super(props);    this.state = {      data: props.data,    };  }  componentDidMount() {      this.getCharts();  }  // eslint-disable-next-line no-unused-vars  componentWillReceiveProps(nextProps, nextContext) {    if (nextProps.data.length > 0) {      this.setState({        data: nextProps.data,      });      setTimeout(() => {        this.getCharts();      }, 500);    }  }  getCharts = () => {    const { data } = this.state;    const gaoData=[];    const massData=[];    // eslint-disable-next-line array-callback-return      data.map(item=>{        gaoData.push({ lng:item.longitude, lat:item.latitude, count:item.number})        massData.push({lnglat:[item.longitude,item.latitude],val:item.number})      });    console.log("高德地图",gaoData);    const map = new AMap.Map('gaoDe', {      resizeEnable: true,      center: [108.5, 34.3],      zoom: 4    });    let heatmap;    map.plugin(["AMap.Heatmap","AMap.Scale",'AMap.ToolBar',], function () {      // 初始化heatmap对象      heatmap = new AMap.Heatmap(map, {        radius: 25, // 给定半径        opacity: [0, 0.8],        gradient:{            0.5: 'blue',            0.65: 'rgb(117,211,248)',            0.7: 'rgb(0, 255, 0)',            0.9: '#ffea00',            1.0: 'red'        }      });      heatmap.setDataSet({        data: gaoData,// heatmapData        max: 10      });      const scale = new AMap.Scale({        visible: true,        offset: new AMap.Pixel(70,20),      });      map.addControl(scale);      map.addControl(new AMap.ToolBar());    });  // 海量点标记    const mass = new AMap.MassMarks(massData, {      opacity: 0.8,      zIndex: 111,      cursor: 'pointer',      style: {        url: 'https://webapi.amap.com/theme/v1.3/markers/n/mark_b.png',        anchor: new AMap.Pixel(6, 6),        size: new AMap.Size(15, 15)      }    });    // var marker = new AMap.Marker({content: ' ', map: map});    // mass.on('mouseover', function (e) {    //   marker.setPosition(e.data.lnglat);    //   marker.setLabel({content: e.data.lnglat})    // });    const infoWindow = new AMap.InfoWindow({offset: new AMap.Pixel(0, -10)});    mass.on('click', function (e) {      infoWindow.setContent(`
标题:热点详细信息
地理位置:${e.data.lnglat.lng}, ${e.data.lnglat.lat}
最近三个月热力值:${e.data.val}
`); infoWindow.open(map, e.data.lnglat); }); mass.setMap(map); // map.setFitView();// 自适应所有的点 // 点不多,添加mark和信息窗(方案一) // const allLength=gaoData.length; // for(let i = 0; i < allLength; i += 1){ // const marker = new AMap.Marker({ // position: [gaoData[i].lng, gaoData[i].lat], // map:map // }); // // const infoWindow = new AMap.InfoWindow({ // anchor: 'bottom-center', // content:`

这是信息窗体!这是信息窗体!

${gaoData[i].lng}

` , // }); // // 鼠标点击marker弹出自定义的信息窗体 // marker.on('click', function () { // infoWindow.open(map,[gaoData[i].lng, gaoData[i].lat]) // }); // } // 点不多,添加mark和信息窗(方案二) // var infoWindow = new AMap.InfoWindow({offset: new AMap.Pixel(0, -30)}); // const allLength=gaoData.length; // function markerClick(e) { // infoWindow.setContent(e.target.content); // infoWindow.open(map, e.target.getPosition()); // } // for(let i = 0; i < allLength; i += 1){ // const marker = new AMap.Marker({ // position: [gaoData[i].lng, gaoData[i].lat], // map:map // }); // marker.content = '我是第' + (i + 1) + '个Marker'; // marker.on('click', markerClick); // } }; render(){ return (
{' '}
10
); }}export default Guide;

然后在其他页面引入这个地图:

import Guidemap from './guidemap';  //引入自己写好的热力地图const arry=[  {longitude:120.328789,latitude:34.876575,number:10}, {longitude:120.328789,latitude:34.876575,number:10},];              //直接在页面引入标签使用  arry的数据格式你可以有自己的格式,不过你的格式改了的话,guide.js参数使用也得自己改下。
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值