百度地图开发入门(4):散点图示例

361 阅读4分钟

一起养成写作习惯!这是我参与「掘金日新计划 · 4 月更文挑战」的第4天,点击查看活动详情

常规的包括散点图、飞线动画、3D建筑等等,这里只会介绍常用的部分,其他的可以去官方文档继续了解学习。也要学会如何快速复用官方的案例。

官方文档:lbsyun.baidu.com/solutions/m…

MapVGL,是一款基于WebGL的地理信息可视化库,可以用来展示大量基于3D的地理信息点线面数据。设计初衷主要是为了解决大数据量的三维地理数据展示问题及一些炫酷的三维效果。

下面会学习一系列案例,可抽象出一个统一的开发模式

1. 引入common库

官方有一个common库可以引入,简化我们部分map的操作:

<!DOCTYPE html>

<html>



<head>

    <script type="text/javascript" src="https://api.map.baidu.com/api?v=1.0&type=webgl&ak=LOaAEpspHorOR4Aq8ifOQpIGbzUuVO4D"></script>

    <!-- 引用mapv相关的js库 -->

    <script src="https://mapv.baidu.com/gl/examples/static/common.js"></script>

    <style>

        html,

        body,

        #map_container {

            width: 100%;

            height: 100%;

            padding: 0;

            margin: 0;

        }

        /* 隐藏百度的下面log和版权声明 */

        .anchrolBL, BMap_cpyCtrl {

            display: none;

        }

    </style>

</head>



<body>

    <div id="map_container"></div>

    <script>

        

        // 引入的common库所作的处理

        const map = initMap({

            center: [121.477091,31.753594],

            zoom: 10,

            style: snowStyle,

            tilt: 0

        })





    </script>

</body>



</html>

记得id要改一下,或者拷贝一份改他的源代码

2. 绘制一个点

主要步骤分为准备数据源与绘制数据

<!DOCTYPE html>

<html>



<head>

    <script type="text/javascript" src="https://api.map.baidu.com/api?v=1.0&type=webgl&ak=LOaAEpspHorOR4Aq8ifOQpIGbzUuVO4D"></script>

    <!-- 引用mapv相关的js库 -->

    <script src="https://mapv.baidu.com/gl/examples/static/common.js"></script>

    <script src="https://mapv.baidu.com/build/mapv.js"></script>

    <script src="https://code.bdstatic.com/npm/mapvgl@1.0.0-beta.124/dist/mapvgl.min.js"></script>

    <style>

        html,

        body,

        #map_container {

            width: 100%;

            height: 100%;

            padding: 0;

            margin: 0;

        }

        /* 隐藏百度的下面log和版权声明 */

        .anchrolBL, BMap_cpyCtrl {

            display: none;

        }

    </style>

</head>



<body>

    <div id="map_container"></div>

    <script>

        

        // 引入的common库所作的处理

        // mapv提供了api,根据名称获取坐标

        const cities = ['上海'];

        const cityCenter = mapv.utilCityCenter.getCenterByCityName(cities[0]);

        const map = initMap({

            center: [cityCenter.lng,cityCenter.lat],

            zoom: 10,

            style: snowStyle,

            tilt: 0

        })



        // 准备数据源

        const data = [];

        data.push({

            // 拿到地理信息,包括一个坐标

            geometry: {

                type: 'Point',

                coordinates: [cityCenter.lng, cityCenter.lat]

            }

        });



        // 绘制数据源

        // 1. 生成mapvgl的视图View - mapvgl的画布图层

        const view = new mapvgl.View({map});

        // 2. 初始化 mapvgl 的PointLayer图层对象

        const pointLayer = new mapvgl.PointLayer({});

        // 3. 将 PointLayer 对象加入View中

        view.addLayer(pointLayer)

        // 4. 将 data与point进行绑定

        pointLayer.setData(data);





    </script>

</body>



</html>

3. 增加数据源

这里我们借助官方文档示例,多选取一些城市点并选取一些随机偏差生成700个点:

<!DOCTYPE html>

<html>



<head>

    <script type="text/javascript"

        src="https://api.map.baidu.com/api?v=1.0&type=webgl&ak=LOaAEpspHorOR4Aq8ifOQpIGbzUuVO4D"></script>

    <!-- 引用mapv相关的js库 -->

    <script src="https://mapv.baidu.com/gl/examples/static/common.js"></script>

    <script src="https://mapv.baidu.com/build/mapv.js"></script>

    <script src="https://code.bdstatic.com/npm/mapvgl@1.0.0-beta.124/dist/mapvgl.min.js"></script>

    <style>

        html,

        body,

        #map_container {

            width: 100%;

            height: 100%;

            padding: 0;

            margin: 0;

        }



        /* 隐藏百度的下面log和版权声明 */

        .anchrolBL,

        BMap_cpyCtrl {

            display: none;

        }

    </style>

</head>



<body>

    <div id="map_container"></div>

    <script>

        const map = initBMap();

        const data = initData();

        setData(data, map);



        // 初始化百度地图

        function initBMap() {

            // 引入的common库所作的处理

            // mapv提供了api,根据名称获取坐标

            const cityCenter = mapv.utilCityCenter.getCenterByCityName('南京');

            const map = initMap({

                center: [cityCenter.lng, cityCenter.lat],

                zoom: 10,

                style: snowStyle,

                tilt: 0

            })

            return map;



        }





        // 准备数据源

        function initData() {

            const data = [];

            // 随机拿700个地图点,后续会构造随机点

            let random = 700;

            const cities = [

                '北京', '天津', '上海', '重庆', '石家庄', '太原', '呼和浩特', '哈尔滨',

                '长春', '沈阳', '济南', '南京', '合肥', '杭州', '南昌', '福州', '郑州',

                '武汉', '长沙', '广州', '南宁', '西安', '银川', '兰州', '西宁', '乌鲁木齐',

                '成都', '贵阳', '昆明', '拉萨', '海口'

            ];

            while (random--) {

                const cityCenter = mapv.utilCityCenter.getCenterByCityName(cities[parseInt(Math.random() * cities.length)]);

                data.push({

                    // 拿到地理信息,包括一个坐标

                    // 添加一个偏移量,以获得更多点

                    geometry: {

                        type: 'Point',

                        coordinates: [cityCenter.lng - 2 + Math.random() * 4, cityCenter.lat - 2 + Math.random() * 4]

                    }

                });

            }

            console.log(data);

            return data;

        }





        // 绘制数据源 

        function setData(data, map) {

            // 1. 生成mapvgl的视图View - mapvgl的画布图层

            const view = new mapvgl.View({ map });

            // 2. 初始化 mapvgl 的PointLayer图层对象

            const pointLayer = new mapvgl.PointLayer({});

            // 3. 将 PointLayer 对象加入View中

            view.addLayer(pointLayer)

            // 4. 将 data与point进行绑定

            pointLayer.setData(data);



        }







    </script>

</body>



</html>

4. 通过点大小与颜色深浅表示数据

但是如果结合实际业务场景,例如想要直观展示每个城市的电商销售数据,就需要点可以根据数据的大小以及颜色深浅而呈现数据状态。

首先我们需要添加一个销售数据,这里我们再生成data时新增一个属性就好:

// 准备数据源

        function initData() {

            const data = [];

            // 随机拿700个地图点,后续会构造随机点

            let random = 700;

            const cities = [

                '北京', '天津', '上海', '重庆', '石家庄', '太原', '呼和浩特', '哈尔滨',

                '长春', '沈阳', '济南', '南京', '合肥', '杭州', '南昌', '福州', '郑州',

                '武汉', '长沙', '广州', '南宁', '西安', '银川', '兰州', '西宁', '乌鲁木齐',

                '成都', '贵阳', '昆明', '拉萨', '海口'

            ];

            while (random--) {

                const cityCenter = mapv.utilCityCenter.getCenterByCityName(cities[parseInt(Math.random() * cities.length)]);

                data.push({

                    // 拿到地理信息,包括一个坐标

                    // 添加一个偏移量,以获得更多点

                    geometry: {

                        type: 'Point',

                        coordinates: [cityCenter.lng - 2 + Math.random() * 4, cityCenter.lat - 2 + Math.random() * 4]

                    },

                    // 代表销量

                    properties: {

                        sales: Math.random() * 100

                    }

                });

            }

            console.log(data);

            return data;

        }

接着我们需要在setData里面初始化图层的时候来控制Size,这里我们可以借助Intensity对象来更好的限制和控制点的大小:

// 绘制数据源 

        function setData(data, map) {

            // 1. 生成mapvgl的视图View - mapvgl的画布图层

            const view = new mapvgl.View({ map });

            // 2. 初始化Intensity对象 - 控制图上点的大小

            const intensity = new mapvgl.Intensity({

                min: 0, // 范围

                max: 100,

                minSize:5,  // 最小最大点像素大小

                maxSize:30

            });

            // 3. 初始化 mapvgl 的PointLayer图层对象

            const pointLayer = new mapvgl.PointLayer({

                size: function(data){

                    // 直接返回点太大了

                    // return parseInt(data.properties.sales)

                    return intensity.getSize(data.properties.sales);

                },

                // color: function(data){

                    

                // }

            });

            // 4. 将 PointLayer 对象加入View中

            view.addLayer(pointLayer)

            // 5. 将 data与point进行绑定

            pointLayer.setData(data);



        }

好了,接着我们再借助颜色角度来表达数据内容,同样借助intensity对象,并回调控制color:

// 绘制数据源 

        function setData(data, map) {

            // 1. 生成mapvgl的视图View - mapvgl的画布图层

            const view = new mapvgl.View({ map });

            // 2. 初始化Intensity对象 - 控制图上点的大小

            const intensity = new mapvgl.Intensity({

                min: 0, // 范围

                max: 100,

                minSize:5,  // 最小最大点像素大小

                maxSize:30,

                // 渐变 - 允许输入0-1之间的颜色变化

                gradient: {

                    0:'rgba(25, 66, 102,0.8)',

                    0.3: 'rgba(145,102,129,0.8)',

                    0.7: 'rgba(210,131,137,0.8)',

                    1: 'rgba(248,177,149,0.8)'

                }

            });

            // 3. 初始化 mapvgl 的PointLayer图层对象

            const pointLayer = new mapvgl.PointLayer({

                size: function(data){

                    // 直接返回点太大了

                    // return parseInt(data.properties.sales)

                    return intensity.getSize(data.properties.sales);

                },

                color: function(data){

                    return intensity.getColor(data.properties.sales);

                }

            });

            // 4. 将 PointLayer 对象加入View中

            view.addLayer(pointLayer)

            // 5. 将 data与point进行绑定

            pointLayer.setData(data);



        }

5. 数据筛选

同时有时候我们只会关注一些头部数据,可以对data进行筛选:

 // 准备数据源

        function initData() {

            let data = [];

            // 随机拿700个地图点,后续会构造随机点

            let random = 700;

            const cities = [

                '北京', '天津', '上海', '重庆', '石家庄', '太原', '呼和浩特', '哈尔滨',

                '长春', '沈阳', '济南', '南京', '合肥', '杭州', '南昌', '福州', '郑州',

                '武汉', '长沙', '广州', '南宁', '西安', '银川', '兰州', '西宁', '乌鲁木齐',

                '成都', '贵阳', '昆明', '拉萨', '海口'

            ];

            while (random--) {

                const cityCenter = mapv.utilCityCenter.getCenterByCityName(cities[parseInt(Math.random() * cities.length)]);

                data.push({

                    // 拿到地理信息,包括一个坐标

                    // 添加一个偏移量,以获得更多点

                    geometry: {

                        type: 'Point',

                        coordinates: [cityCenter.lng - 2 + Math.random() * 4, cityCenter.lat - 2 + Math.random() * 4]

                    },

                    // 代表销量

                    properties: {

                        sales: Math.random() * 100

                    }

                });

            }

            console.log(data);

            data = data.filter(value => value.properties.sales > 50);

            return data;

        }

6. 流程总结

初始化百度地图对象

数据源初始化:提供数据,包括业务数据

绘制数据:通过webgl生成视图并初始化intensity对象帮助控制点,然后生成layer并计算size和color,最后将layer加入视图中并进行数据绑定